diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2018-01-29 16:37:15 -0800 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2018-01-29 16:37:15 -0800 |
commit | aca21de2e8355769513c27d1c218e3e8947fe84b (patch) | |
tree | 1a79f8baa76c9828c36c3331628eb4f10be7b214 | |
parent | 31466f3ed710e5761077190809e694f55aed5deb (diff) | |
parent | 2334b1ac1235934fc196f2d25bae7f348d3bf42e (diff) | |
download | linux-aca21de2e8355769513c27d1c218e3e8947fe84b.tar.bz2 |
Merge tag 'm68k-for-v4.16-tag1' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k
Pull m68k updates from Geert Uytterhoeven:
- first part of an overhaul of the NuBus subsystem, to bring it up to
modern driver model standards
- a race condition fix for Mac
- defconfig updates
* tag 'm68k-for-v4.16-tag1' of git://git.kernel.org/pub/scm/linux/kernel/git/geert/linux-m68k:
MAINTAINERS: Add NuBus subsystem entry
m68k/mac: Fix race conditions in OSS interrupt dispatch
nubus: Add support for the driver model
nubus: Add expansion_type values for various Mac models
nubus: Adopt standard linked list implementation
nubus: Rename struct nubus_dev
nubus: Rework /proc/bus/nubus/s/ implementation
nubus: Generalize block resource handling
nubus: Clean up whitespace
nubus: Remove redundant code
nubus: Call proc_mkdir() not more than once per slot directory
nubus: Validate slot resource IDs
nubus: Fix log spam
nubus: Use static functions where possible
nubus: Fix up header split
nubus: Avoid array underflow and overflow
m68k/defconfig: Update defconfigs for v4.15-rc1
26 files changed, 833 insertions, 651 deletions
diff --git a/MAINTAINERS b/MAINTAINERS index a9c9c9ff72d8..9e8de5670e68 100644 --- a/MAINTAINERS +++ b/MAINTAINERS @@ -9757,6 +9757,15 @@ S: Supported F: Documentation/filesystems/ntfs.txt F: fs/ntfs/ +NUBUS SUBSYSTEM +M: Finn Thain <fthain@telegraphics.com.au> +L: linux-m68k@lists.linux-m68k.org +S: Maintained +F: arch/*/include/asm/nubus.h +F: drivers/nubus/ +F: include/linux/nubus.h +F: include/uapi/linux/nubus.h + NVIDIA (rivafb and nvidiafb) FRAMEBUFFER DRIVER M: Antonino Daplas <adaplas@gmail.com> L: linux-fbdev@vger.kernel.org diff --git a/arch/m68k/configs/amiga_defconfig b/arch/m68k/configs/amiga_defconfig index 5b5fa9831b4d..e0b285e1e75f 100644 --- a/arch/m68k/configs/amiga_defconfig +++ b/arch/m68k/configs/amiga_defconfig @@ -454,7 +454,6 @@ CONFIG_PPS_CLIENT_LDISC=m CONFIG_PPS_CLIENT_PARPORT=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FB_CIRRUS=y CONFIG_FB_AMIGA=y @@ -595,6 +594,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -624,6 +624,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -653,3 +654,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/apollo_defconfig b/arch/m68k/configs/apollo_defconfig index 72a7764b74ed..3281026a3e15 100644 --- a/arch/m68k/configs/apollo_defconfig +++ b/arch/m68k/configs/apollo_defconfig @@ -422,7 +422,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FRAMEBUFFER_CONSOLE=y CONFIG_LOGO=y @@ -554,6 +553,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -583,6 +583,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -612,3 +613,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/atari_defconfig b/arch/m68k/configs/atari_defconfig index 884b43a2f0d9..e943fad480cf 100644 --- a/arch/m68k/configs/atari_defconfig +++ b/arch/m68k/configs/atari_defconfig @@ -437,7 +437,6 @@ CONFIG_PPS_CLIENT_LDISC=m CONFIG_PPS_CLIENT_PARPORT=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FB_ATARI=y CONFIG_FRAMEBUFFER_CONSOLE=y @@ -576,6 +575,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -605,6 +605,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -634,3 +635,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/bvme6000_defconfig b/arch/m68k/configs/bvme6000_defconfig index fcfa60d31499..700c2310c336 100644 --- a/arch/m68k/configs/bvme6000_defconfig +++ b/arch/m68k/configs/bvme6000_defconfig @@ -420,7 +420,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_HID=m CONFIG_HIDRAW=y CONFIG_UHID=m @@ -546,6 +545,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -575,6 +575,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -604,3 +605,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/hp300_defconfig b/arch/m68k/configs/hp300_defconfig index 9d597bbbbbfe..271d57fa4301 100644 --- a/arch/m68k/configs/hp300_defconfig +++ b/arch/m68k/configs/hp300_defconfig @@ -425,7 +425,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FRAMEBUFFER_CONSOLE=y CONFIG_LOGO=y @@ -556,6 +555,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -585,6 +585,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -614,3 +615,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/mac_defconfig b/arch/m68k/configs/mac_defconfig index 45da20d1286c..88761b867975 100644 --- a/arch/m68k/configs/mac_defconfig +++ b/arch/m68k/configs/mac_defconfig @@ -447,7 +447,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FB_VALKYRIE=y CONFIG_FB_MAC=y @@ -578,6 +577,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -607,6 +607,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -636,3 +637,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/multi_defconfig b/arch/m68k/configs/multi_defconfig index fda880c10861..7cb35dadf03b 100644 --- a/arch/m68k/configs/multi_defconfig +++ b/arch/m68k/configs/multi_defconfig @@ -504,7 +504,6 @@ CONFIG_PPS_CLIENT_LDISC=m CONFIG_PPS_CLIENT_PARPORT=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FB_CIRRUS=y CONFIG_FB_AMIGA=y @@ -658,6 +657,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -687,6 +687,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -716,3 +717,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/mvme147_defconfig b/arch/m68k/configs/mvme147_defconfig index 7d5e4863efec..b139d7b68393 100644 --- a/arch/m68k/configs/mvme147_defconfig +++ b/arch/m68k/configs/mvme147_defconfig @@ -420,7 +420,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_HID=m CONFIG_HIDRAW=y CONFIG_UHID=m @@ -546,6 +545,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -575,6 +575,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -604,3 +605,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/mvme16x_defconfig b/arch/m68k/configs/mvme16x_defconfig index 7763b71a9c49..398346138769 100644 --- a/arch/m68k/configs/mvme16x_defconfig +++ b/arch/m68k/configs/mvme16x_defconfig @@ -420,7 +420,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_HID=m CONFIG_HIDRAW=y CONFIG_UHID=m @@ -546,6 +545,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -575,6 +575,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -604,3 +605,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/q40_defconfig b/arch/m68k/configs/q40_defconfig index 17eaebfa3e19..14c608326f6d 100644 --- a/arch/m68k/configs/q40_defconfig +++ b/arch/m68k/configs/q40_defconfig @@ -437,7 +437,6 @@ CONFIG_PPS_CLIENT_LDISC=m CONFIG_PPS_CLIENT_PARPORT=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FRAMEBUFFER_CONSOLE=y CONFIG_LOGO=y @@ -569,6 +568,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -598,6 +598,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -627,3 +628,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/sun3_defconfig b/arch/m68k/configs/sun3_defconfig index d1cb7a04ae1d..97dec0bf52f1 100644 --- a/arch/m68k/configs/sun3_defconfig +++ b/arch/m68k/configs/sun3_defconfig @@ -419,7 +419,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FRAMEBUFFER_CONSOLE=y CONFIG_LOGO=y @@ -548,6 +547,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -576,6 +576,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -605,3 +606,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/configs/sun3x_defconfig b/arch/m68k/configs/sun3x_defconfig index ea3a331c62d5..56df28d6d91d 100644 --- a/arch/m68k/configs/sun3x_defconfig +++ b/arch/m68k/configs/sun3x_defconfig @@ -419,7 +419,6 @@ CONFIG_NTP_PPS=y CONFIG_PPS_CLIENT_LDISC=m CONFIG_PTP_1588_CLOCK=m # CONFIG_HWMON is not set -# CONFIG_RC_CORE is not set CONFIG_FB=y CONFIG_FRAMEBUFFER_CONSOLE=y CONFIG_LOGO=y @@ -548,6 +547,7 @@ CONFIG_TEST_RHASHTABLE=m CONFIG_TEST_HASH=m CONFIG_TEST_USER_COPY=m CONFIG_TEST_BPF=m +CONFIG_TEST_FIND_BIT=m CONFIG_TEST_FIRMWARE=m CONFIG_TEST_SYSCTL=m CONFIG_TEST_UDELAY=m @@ -577,6 +577,7 @@ CONFIG_CRYPTO_RMD256=m CONFIG_CRYPTO_RMD320=m CONFIG_CRYPTO_SHA512=m CONFIG_CRYPTO_SHA3=m +CONFIG_CRYPTO_SM3=m CONFIG_CRYPTO_TGR192=m CONFIG_CRYPTO_WP512=m CONFIG_CRYPTO_AES_TI=m @@ -606,3 +607,4 @@ CONFIG_CRYPTO_USER_API_AEAD=m # CONFIG_CRYPTO_HW is not set CONFIG_CRC32_SELFTEST=m CONFIG_XZ_DEC_TEST=m +CONFIG_STRING_SELFTEST=m diff --git a/arch/m68k/include/asm/macintosh.h b/arch/m68k/include/asm/macintosh.h index f42c27400dbc..9b840c03ebb7 100644 --- a/arch/m68k/include/asm/macintosh.h +++ b/arch/m68k/include/asm/macintosh.h @@ -33,7 +33,7 @@ struct mac_model char ide_type; char scc_type; char ether_type; - char nubus_type; + char expansion_type; char floppy_type; }; @@ -73,8 +73,11 @@ struct mac_model #define MAC_ETHER_SONIC 1 #define MAC_ETHER_MACE 2 -#define MAC_NO_NUBUS 0 -#define MAC_NUBUS 1 +#define MAC_EXP_NONE 0 +#define MAC_EXP_PDS 1 /* Accepts only a PDS card */ +#define MAC_EXP_NUBUS 2 /* Accepts only NuBus card(s) */ +#define MAC_EXP_PDS_NUBUS 3 /* Accepts PDS card and/or NuBus card(s) */ +#define MAC_EXP_PDS_COMM 4 /* Accepts PDS card or Comm Slot card */ #define MAC_FLOPPY_IWM 0 #define MAC_FLOPPY_SWIM_ADDR1 1 diff --git a/arch/m68k/mac/config.c b/arch/m68k/mac/config.c index 16cd5cea5207..d3d435248a24 100644 --- a/arch/m68k/mac/config.c +++ b/arch/m68k/mac/config.c @@ -212,7 +212,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_II, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_IWM, }, @@ -227,7 +227,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_II, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_IWM, }, { .ident = MAC_MODEL_IIX, @@ -236,7 +236,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_II, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_IICX, @@ -245,7 +245,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_II, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_SE30, @@ -254,7 +254,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_II, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -272,7 +272,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_IIFX, @@ -281,7 +281,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_IIFX, .scc_type = MAC_SCC_IOP, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_IOP, }, { .ident = MAC_MODEL_IISI, @@ -290,7 +290,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_IIVI, @@ -299,7 +299,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_IIVX, @@ -308,7 +308,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -323,7 +323,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_CCL, @@ -332,7 +331,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_CCLII, @@ -341,7 +340,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -356,7 +355,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_LCII, @@ -365,7 +364,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_LCIII, @@ -374,7 +373,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -395,7 +394,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_Q605_ACC, @@ -404,7 +403,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_Q610, @@ -414,7 +413,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_Q630, @@ -424,8 +423,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .ide_type = MAC_IDE_QUADRA, .scc_type = MAC_SCC_QUADRA, - .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_COMM, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_Q650, @@ -435,7 +433,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, /* The Q700 does have a NS Sonic */ @@ -447,7 +445,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA2, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_Q800, @@ -457,7 +455,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_Q840, @@ -467,7 +465,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA3, .scc_type = MAC_SCC_PSC, .ether_type = MAC_ETHER_MACE, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_AV, }, { .ident = MAC_MODEL_Q900, @@ -477,7 +475,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA2, .scc_type = MAC_SCC_IOP, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_IOP, }, { .ident = MAC_MODEL_Q950, @@ -487,7 +485,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA2, .scc_type = MAC_SCC_IOP, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_IOP, }, @@ -502,7 +500,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_P475, @@ -511,7 +509,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_P475F, @@ -520,7 +518,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_P520, @@ -529,7 +527,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_P550, @@ -538,7 +536,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, /* These have the comm slot, and therefore possibly SONIC ethernet */ @@ -549,8 +547,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_II, - .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_COMM, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_P588, @@ -560,8 +557,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .ide_type = MAC_IDE_QUADRA, .scc_type = MAC_SCC_II, - .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_COMM, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_TV, @@ -570,7 +566,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_P600, @@ -579,7 +574,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_LC, .scc_type = MAC_SCC_II, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -596,7 +591,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_C650, @@ -606,7 +601,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR1, }, { .ident = MAC_MODEL_C660, @@ -616,7 +611,7 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_QUADRA3, .scc_type = MAC_SCC_PSC, .ether_type = MAC_ETHER_MACE, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_PDS_NUBUS, .floppy_type = MAC_FLOPPY_AV, }, @@ -633,7 +628,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB145, @@ -642,7 +636,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB150, @@ -652,7 +645,6 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_OLD, .ide_type = MAC_IDE_PB, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB160, @@ -661,7 +653,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB165, @@ -670,7 +661,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB165C, @@ -679,7 +669,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB170, @@ -688,7 +677,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB180, @@ -697,7 +685,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB180C, @@ -706,7 +693,6 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_QUADRA, .scsi_type = MAC_SCSI_OLD, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB190, @@ -716,7 +702,6 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_LATE, .ide_type = MAC_IDE_BABOON, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB520, @@ -726,7 +711,6 @@ static struct mac_model mac_data_table[] = { .scsi_type = MAC_SCSI_LATE, .scc_type = MAC_SCC_QUADRA, .ether_type = MAC_ETHER_SONIC, - .nubus_type = MAC_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -743,7 +727,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_DUO, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB230, @@ -752,7 +736,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_DUO, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB250, @@ -761,7 +745,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_DUO, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB270C, @@ -770,7 +754,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_DUO, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB280, @@ -779,7 +763,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_DUO, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, { .ident = MAC_MODEL_PB280C, @@ -788,7 +772,7 @@ static struct mac_model mac_data_table[] = { .via_type = MAC_VIA_IICI, .scsi_type = MAC_SCSI_DUO, .scc_type = MAC_SCC_QUADRA, - .nubus_type = MAC_NUBUS, + .expansion_type = MAC_EXP_NUBUS, .floppy_type = MAC_FLOPPY_SWIM_ADDR2, }, @@ -1100,14 +1084,12 @@ int __init mac_platform_init(void) * Ethernet device */ - switch (macintosh_config->ether_type) { - case MAC_ETHER_SONIC: + if (macintosh_config->ether_type == MAC_ETHER_SONIC || + macintosh_config->expansion_type == MAC_EXP_PDS_COMM) platform_device_register_simple("macsonic", -1, NULL, 0); - break; - case MAC_ETHER_MACE: + + if (macintosh_config->ether_type == MAC_ETHER_MACE) platform_device_register_simple("macmace", -1, NULL, 0); - break; - } return 0; } diff --git a/arch/m68k/mac/oss.c b/arch/m68k/mac/oss.c index 3f81892527ad..921e6c092f2c 100644 --- a/arch/m68k/mac/oss.c +++ b/arch/m68k/mac/oss.c @@ -53,56 +53,41 @@ void __init oss_init(void) } /* - * Handle miscellaneous OSS interrupts. + * Handle OSS interrupts. + * XXX how do you clear a pending IRQ? is it even necessary? */ -static void oss_irq(struct irq_desc *desc) +static void oss_iopism_irq(struct irq_desc *desc) { - int events = oss->irq_pending & - (OSS_IP_IOPSCC | OSS_IP_SCSI | OSS_IP_IOPISM); - - if (events & OSS_IP_IOPSCC) { - oss->irq_pending &= ~OSS_IP_IOPSCC; - generic_handle_irq(IRQ_MAC_SCC); - } - - if (events & OSS_IP_SCSI) { - oss->irq_pending &= ~OSS_IP_SCSI; - generic_handle_irq(IRQ_MAC_SCSI); - } - - if (events & OSS_IP_IOPISM) { - oss->irq_pending &= ~OSS_IP_IOPISM; - generic_handle_irq(IRQ_MAC_ADB); - } + generic_handle_irq(IRQ_MAC_ADB); } -/* - * Nubus IRQ handler, OSS style - * - * Unlike the VIA/RBV this is on its own autovector interrupt level. - */ +static void oss_scsi_irq(struct irq_desc *desc) +{ + generic_handle_irq(IRQ_MAC_SCSI); +} static void oss_nubus_irq(struct irq_desc *desc) { - int events, irq_bit, i; + u16 events, irq_bit; + int irq_num; events = oss->irq_pending & OSS_IP_NUBUS; - if (!events) - return; - - /* There are only six slots on the OSS, not seven */ - - i = 6; - irq_bit = 0x40; + irq_num = NUBUS_SOURCE_BASE + 5; + irq_bit = OSS_IP_NUBUS5; do { - --i; - irq_bit >>= 1; if (events & irq_bit) { - oss->irq_pending &= ~irq_bit; - generic_handle_irq(NUBUS_SOURCE_BASE + i); + events &= ~irq_bit; + generic_handle_irq(irq_num); } - } while(events & (irq_bit - 1)); + --irq_num; + irq_bit >>= 1; + } while (events); +} + +static void oss_iopscc_irq(struct irq_desc *desc) +{ + generic_handle_irq(IRQ_MAC_SCC); } /* @@ -122,14 +107,14 @@ static void oss_nubus_irq(struct irq_desc *desc) void __init oss_register_interrupts(void) { - irq_set_chained_handler(OSS_IRQLEV_IOPISM, oss_irq); - irq_set_chained_handler(OSS_IRQLEV_SCSI, oss_irq); + irq_set_chained_handler(OSS_IRQLEV_IOPISM, oss_iopism_irq); + irq_set_chained_handler(OSS_IRQLEV_SCSI, oss_scsi_irq); irq_set_chained_handler(OSS_IRQLEV_NUBUS, oss_nubus_irq); - irq_set_chained_handler(OSS_IRQLEV_IOPSCC, oss_irq); + irq_set_chained_handler(OSS_IRQLEV_IOPSCC, oss_iopscc_irq); irq_set_chained_handler(OSS_IRQLEV_VIA1, via1_irq); /* OSS_VIA1 gets enabled here because it has no machspec interrupt. */ - oss->irq_level[OSS_VIA1] = IRQ_AUTO_6; + oss->irq_level[OSS_VIA1] = OSS_IRQLEV_VIA1; } /* diff --git a/drivers/net/ethernet/8390/mac8390.c b/drivers/net/ethernet/8390/mac8390.c index 9497f18eaba0..2f91ce8dc614 100644 --- a/drivers/net/ethernet/8390/mac8390.c +++ b/drivers/net/ethernet/8390/mac8390.c @@ -123,7 +123,8 @@ enum mac8390_access { }; extern int mac8390_memtest(struct net_device *dev); -static int mac8390_initdev(struct net_device *dev, struct nubus_dev *ndev, +static int mac8390_initdev(struct net_device *dev, + struct nubus_rsrc *ndev, enum mac8390_type type); static int mac8390_open(struct net_device *dev); @@ -169,11 +170,11 @@ static void word_memcpy_tocard(unsigned long tp, const void *fp, int count); static void word_memcpy_fromcard(void *tp, unsigned long fp, int count); static u32 mac8390_msg_enable; -static enum mac8390_type __init mac8390_ident(struct nubus_dev *dev) +static enum mac8390_type __init mac8390_ident(struct nubus_rsrc *fres) { - switch (dev->dr_sw) { + switch (fres->dr_sw) { case NUBUS_DRSW_3COM: - switch (dev->dr_hw) { + switch (fres->dr_hw) { case NUBUS_DRHW_APPLE_SONIC_NB: case NUBUS_DRHW_APPLE_SONIC_LC: case NUBUS_DRHW_SONNET: @@ -184,7 +185,7 @@ static enum mac8390_type __init mac8390_ident(struct nubus_dev *dev) break; case NUBUS_DRSW_APPLE: - switch (dev->dr_hw) { + switch (fres->dr_hw) { case NUBUS_DRHW_ASANTE_LC: return MAC8390_NONE; case NUBUS_DRHW_CABLETRON: @@ -201,7 +202,7 @@ static enum mac8390_type __init mac8390_ident(struct nubus_dev *dev) case NUBUS_DRSW_TECHWORKS: case NUBUS_DRSW_DAYNA2: case NUBUS_DRSW_DAYNA_LC: - if (dev->dr_hw == NUBUS_DRHW_CABLETRON) + if (fres->dr_hw == NUBUS_DRHW_CABLETRON) return MAC8390_CABLETRON; else return MAC8390_APPLE; @@ -212,7 +213,7 @@ static enum mac8390_type __init mac8390_ident(struct nubus_dev *dev) break; case NUBUS_DRSW_KINETICS: - switch (dev->dr_hw) { + switch (fres->dr_hw) { case NUBUS_DRHW_INTERLAN: return MAC8390_INTERLAN; default: @@ -225,8 +226,8 @@ static enum mac8390_type __init mac8390_ident(struct nubus_dev *dev) * These correspond to Dayna Sonic cards * which use the macsonic driver */ - if (dev->dr_hw == NUBUS_DRHW_SMC9194 || - dev->dr_hw == NUBUS_DRHW_INTERLAN) + if (fres->dr_hw == NUBUS_DRHW_SMC9194 || + fres->dr_hw == NUBUS_DRHW_INTERLAN) return MAC8390_NONE; else return MAC8390_DAYNA; @@ -289,7 +290,8 @@ static int __init mac8390_memsize(unsigned long membase) return i * 0x1000; } -static bool __init mac8390_init(struct net_device *dev, struct nubus_dev *ndev, +static bool __init mac8390_init(struct net_device *dev, + struct nubus_rsrc *ndev, enum mac8390_type cardtype) { struct nubus_dir dir; @@ -394,7 +396,7 @@ static bool __init mac8390_init(struct net_device *dev, struct nubus_dev *ndev, struct net_device * __init mac8390_probe(int unit) { struct net_device *dev; - struct nubus_dev *ndev = NULL; + struct nubus_rsrc *ndev = NULL; int err = -ENODEV; struct ei_device *ei_local; @@ -414,8 +416,11 @@ struct net_device * __init mac8390_probe(int unit) if (unit >= 0) sprintf(dev->name, "eth%d", unit); - while ((ndev = nubus_find_type(NUBUS_CAT_NETWORK, NUBUS_TYPE_ETHERNET, - ndev))) { + for_each_func_rsrc(ndev) { + if (ndev->category != NUBUS_CAT_NETWORK || + ndev->type != NUBUS_TYPE_ETHERNET) + continue; + /* Have we seen it already? */ if (slots & (1 << ndev->board->slot)) continue; @@ -489,7 +494,7 @@ static const struct net_device_ops mac8390_netdev_ops = { }; static int __init mac8390_initdev(struct net_device *dev, - struct nubus_dev *ndev, + struct nubus_rsrc *ndev, enum mac8390_type type) { static u32 fwrd4_offsets[16] = { diff --git a/drivers/net/ethernet/cirrus/mac89x0.c b/drivers/net/ethernet/cirrus/mac89x0.c index f910f0f386d6..977d4c2c759d 100644 --- a/drivers/net/ethernet/cirrus/mac89x0.c +++ b/drivers/net/ethernet/cirrus/mac89x0.c @@ -187,6 +187,7 @@ struct net_device * __init mac89x0_probe(int unit) unsigned long ioaddr; unsigned short sig; int err = -ENODEV; + struct nubus_rsrc *fres; if (!MACH_IS_MAC) return ERR_PTR(-ENODEV); @@ -207,8 +208,9 @@ struct net_device * __init mac89x0_probe(int unit) /* We might have to parameterize this later */ slot = 0xE; /* Get out now if there's a real NuBus card in slot E */ - if (nubus_find_slot(slot, NULL) != NULL) - goto out; + for_each_func_rsrc(fres) + if (fres->board->slot == slot) + goto out; /* The pseudo-ISA bits always live at offset 0x300 (gee, wonder why...) */ diff --git a/drivers/net/ethernet/natsemi/macsonic.c b/drivers/net/ethernet/natsemi/macsonic.c index a42433fb6949..b922ab5cedea 100644 --- a/drivers/net/ethernet/natsemi/macsonic.c +++ b/drivers/net/ethernet/natsemi/macsonic.c @@ -311,7 +311,7 @@ static int mac_onboard_sonic_probe(struct net_device *dev) { struct sonic_local* lp = netdev_priv(dev); int sr; - int commslot = 0; + bool commslot = macintosh_config->expansion_type == MAC_EXP_PDS_COMM; if (!MACH_IS_MAC) return -ENODEV; @@ -322,10 +322,7 @@ static int mac_onboard_sonic_probe(struct net_device *dev) Ethernet (BTW, the Ethernet *is* always at the same address, and nothing else lives there, at least if Apple's documentation is to be believed) */ - if (macintosh_config->ident == MAC_MODEL_Q630 || - macintosh_config->ident == MAC_MODEL_P588 || - macintosh_config->ident == MAC_MODEL_P575 || - macintosh_config->ident == MAC_MODEL_C610) { + if (commslot || macintosh_config->ident == MAC_MODEL_C610) { int card_present; card_present = hwreg_present((void*)ONBOARD_SONIC_REGISTERS); @@ -333,7 +330,6 @@ static int mac_onboard_sonic_probe(struct net_device *dev) printk("none.\n"); return -ENODEV; } - commslot = 1; } printk("yes\n"); @@ -428,26 +424,26 @@ static int mac_nubus_sonic_ethernet_addr(struct net_device *dev, return 0; } -static int macsonic_ident(struct nubus_dev *ndev) +static int macsonic_ident(struct nubus_rsrc *fres) { - if (ndev->dr_hw == NUBUS_DRHW_ASANTE_LC && - ndev->dr_sw == NUBUS_DRSW_SONIC_LC) + if (fres->dr_hw == NUBUS_DRHW_ASANTE_LC && + fres->dr_sw == NUBUS_DRSW_SONIC_LC) return MACSONIC_DAYNALINK; - if (ndev->dr_hw == NUBUS_DRHW_SONIC && - ndev->dr_sw == NUBUS_DRSW_APPLE) { + if (fres->dr_hw == NUBUS_DRHW_SONIC && + fres->dr_sw == NUBUS_DRSW_APPLE) { /* There has to be a better way to do this... */ - if (strstr(ndev->board->name, "DuoDock")) + if (strstr(fres->board->name, "DuoDock")) return MACSONIC_DUODOCK; else return MACSONIC_APPLE; } - if (ndev->dr_hw == NUBUS_DRHW_SMC9194 && - ndev->dr_sw == NUBUS_DRSW_DAYNA) + if (fres->dr_hw == NUBUS_DRHW_SMC9194 && + fres->dr_sw == NUBUS_DRSW_DAYNA) return MACSONIC_DAYNA; - if (ndev->dr_hw == NUBUS_DRHW_APPLE_SONIC_LC && - ndev->dr_sw == 0) { /* huh? */ + if (fres->dr_hw == NUBUS_DRHW_APPLE_SONIC_LC && + fres->dr_sw == 0) { /* huh? */ return MACSONIC_APPLE16; } return -1; @@ -456,7 +452,7 @@ static int macsonic_ident(struct nubus_dev *ndev) static int mac_nubus_sonic_probe(struct net_device *dev) { static int slots; - struct nubus_dev* ndev = NULL; + struct nubus_rsrc *ndev = NULL; struct sonic_local* lp = netdev_priv(dev); unsigned long base_addr, prom_addr; u16 sonic_dcr; @@ -464,9 +460,11 @@ static int mac_nubus_sonic_probe(struct net_device *dev) int reg_offset, dma_bitmode; /* Find the first SONIC that hasn't been initialized already */ - while ((ndev = nubus_find_type(NUBUS_CAT_NETWORK, - NUBUS_TYPE_ETHERNET, ndev)) != NULL) - { + for_each_func_rsrc(ndev) { + if (ndev->category != NUBUS_CAT_NETWORK || + ndev->type != NUBUS_TYPE_ETHERNET) + continue; + /* Have we seen it already? */ if (slots & (1<<ndev->board->slot)) continue; diff --git a/drivers/nubus/Makefile b/drivers/nubus/Makefile index 21bda2031e7e..6d063cde39d1 100644 --- a/drivers/nubus/Makefile +++ b/drivers/nubus/Makefile @@ -2,6 +2,6 @@ # Makefile for the nubus specific drivers. # -obj-y := nubus.o +obj-y := nubus.o bus.o obj-$(CONFIG_PROC_FS) += proc.o diff --git a/drivers/nubus/bus.c b/drivers/nubus/bus.c new file mode 100644 index 000000000000..d306c348c857 --- /dev/null +++ b/drivers/nubus/bus.c @@ -0,0 +1,117 @@ +// SPDX-License-Identifier: GPL-2.0 +// +// Bus implementation for the NuBus subsystem. +// +// Copyright (C) 2017 Finn Thain + +#include <linux/device.h> +#include <linux/list.h> +#include <linux/nubus.h> +#include <linux/seq_file.h> +#include <linux/slab.h> + +#define to_nubus_board(d) container_of(d, struct nubus_board, dev) +#define to_nubus_driver(d) container_of(d, struct nubus_driver, driver) + +static int nubus_bus_match(struct device *dev, struct device_driver *driver) +{ + return 1; +} + +static int nubus_device_probe(struct device *dev) +{ + struct nubus_driver *ndrv = to_nubus_driver(dev->driver); + int err = -ENODEV; + + if (ndrv->probe) + err = ndrv->probe(to_nubus_board(dev)); + return err; +} + +static int nubus_device_remove(struct device *dev) +{ + struct nubus_driver *ndrv = to_nubus_driver(dev->driver); + int err = -ENODEV; + + if (dev->driver && ndrv->remove) + err = ndrv->remove(to_nubus_board(dev)); + return err; +} + +struct bus_type nubus_bus_type = { + .name = "nubus", + .match = nubus_bus_match, + .probe = nubus_device_probe, + .remove = nubus_device_remove, +}; +EXPORT_SYMBOL(nubus_bus_type); + +int nubus_driver_register(struct nubus_driver *ndrv) +{ + ndrv->driver.bus = &nubus_bus_type; + return driver_register(&ndrv->driver); +} +EXPORT_SYMBOL(nubus_driver_register); + +void nubus_driver_unregister(struct nubus_driver *ndrv) +{ + driver_unregister(&ndrv->driver); +} +EXPORT_SYMBOL(nubus_driver_unregister); + +static struct device nubus_parent = { + .init_name = "nubus", +}; + +int __init nubus_bus_register(void) +{ + int err; + + err = device_register(&nubus_parent); + if (err) + return err; + + err = bus_register(&nubus_bus_type); + if (!err) + return 0; + + device_unregister(&nubus_parent); + return err; +} + +static void nubus_device_release(struct device *dev) +{ + struct nubus_board *board = to_nubus_board(dev); + struct nubus_rsrc *fres, *tmp; + + list_for_each_entry_safe(fres, tmp, &nubus_func_rsrcs, list) + if (fres->board == board) { + list_del(&fres->list); + kfree(fres); + } + kfree(board); +} + +int nubus_device_register(struct nubus_board *board) +{ + board->dev.parent = &nubus_parent; + board->dev.release = nubus_device_release; + board->dev.bus = &nubus_bus_type; + dev_set_name(&board->dev, "slot.%X", board->slot); + return device_register(&board->dev); +} + +static int nubus_print_device_name_fn(struct device *dev, void *data) +{ + struct nubus_board *board = to_nubus_board(dev); + struct seq_file *m = data; + + seq_printf(m, "Slot %X: %s\n", board->slot, board->name); + return 0; +} + +int nubus_proc_show(struct seq_file *m, void *data) +{ + return bus_for_each_dev(&nubus_bus_type, NULL, m, + nubus_print_device_name_fn); +} diff --git a/drivers/nubus/nubus.c b/drivers/nubus/nubus.c index b793727cd4f7..4621ff98138c 100644 --- a/drivers/nubus/nubus.c +++ b/drivers/nubus/nubus.c @@ -15,6 +15,7 @@ #include <linux/errno.h> #include <linux/init.h> #include <linux/module.h> +#include <linux/seq_file.h> #include <linux/slab.h> #include <asm/setup.h> #include <asm/page.h> @@ -31,8 +32,7 @@ /* Globals */ -struct nubus_dev *nubus_devices; -struct nubus_board *nubus_boards; +LIST_HEAD(nubus_func_rsrcs); /* Meaning of "bytelanes": @@ -146,7 +146,7 @@ static inline void *nubus_rom_addr(int slot) return (void *)(0xF1000000 + (slot << 24)); } -static unsigned char *nubus_dirptr(const struct nubus_dirent *nd) +unsigned char *nubus_dirptr(const struct nubus_dirent *nd) { unsigned char *p = nd->base; @@ -161,7 +161,7 @@ static unsigned char *nubus_dirptr(const struct nubus_dirent *nd) pointed to with offsets) out of the card ROM. */ void nubus_get_rsrc_mem(void *dest, const struct nubus_dirent *dirent, - int len) + unsigned int len) { unsigned char *t = (unsigned char *)dest; unsigned char *p = nubus_dirptr(dirent); @@ -173,21 +173,49 @@ void nubus_get_rsrc_mem(void *dest, const struct nubus_dirent *dirent, } EXPORT_SYMBOL(nubus_get_rsrc_mem); -void nubus_get_rsrc_str(void *dest, const struct nubus_dirent *dirent, - int len) +unsigned int nubus_get_rsrc_str(char *dest, const struct nubus_dirent *dirent, + unsigned int len) { - unsigned char *t = (unsigned char *)dest; + char *t = dest; unsigned char *p = nubus_dirptr(dirent); - while (len) { - *t = nubus_get_rom(&p, 1, dirent->mask); - if (!*t++) + while (len > 1) { + unsigned char c = nubus_get_rom(&p, 1, dirent->mask); + + if (!c) break; + *t++ = c; len--; } + if (len > 0) + *t = '\0'; + return t - dest; } EXPORT_SYMBOL(nubus_get_rsrc_str); +void nubus_seq_write_rsrc_mem(struct seq_file *m, + const struct nubus_dirent *dirent, + unsigned int len) +{ + unsigned long buf[32]; + unsigned int buf_size = sizeof(buf); + unsigned char *p = nubus_dirptr(dirent); + + /* If possible, write out full buffers */ + while (len >= buf_size) { + unsigned int i; + + for (i = 0; i < ARRAY_SIZE(buf); i++) + buf[i] = nubus_get_rom(&p, sizeof(buf[0]), + dirent->mask); + seq_write(m, buf, buf_size); + len -= buf_size; + } + /* If not, write out individual bytes */ + while (len--) + seq_putc(m, nubus_get_rom(&p, 1, dirent->mask)); +} + int nubus_get_root_dir(const struct nubus_board *board, struct nubus_dir *dir) { @@ -199,12 +227,11 @@ int nubus_get_root_dir(const struct nubus_board *board, EXPORT_SYMBOL(nubus_get_root_dir); /* This is a slyly renamed version of the above */ -int nubus_get_func_dir(const struct nubus_dev *dev, - struct nubus_dir *dir) +int nubus_get_func_dir(const struct nubus_rsrc *fres, struct nubus_dir *dir) { - dir->ptr = dir->base = dev->directory; + dir->ptr = dir->base = fres->directory; dir->done = 0; - dir->mask = dev->board->lanes; + dir->mask = fres->board->lanes; return 0; } EXPORT_SYMBOL(nubus_get_func_dir); @@ -277,51 +304,20 @@ EXPORT_SYMBOL(nubus_rewinddir); /* Driver interface functions, more or less like in pci.c */ -struct nubus_dev* -nubus_find_device(unsigned short category, unsigned short type, - unsigned short dr_hw, unsigned short dr_sw, - const struct nubus_dev *from) -{ - struct nubus_dev *itor = from ? from->next : nubus_devices; - - while (itor) { - if (itor->category == category && itor->type == type && - itor->dr_hw == dr_hw && itor->dr_sw == dr_sw) - return itor; - itor = itor->next; - } - return NULL; -} -EXPORT_SYMBOL(nubus_find_device); - -struct nubus_dev* -nubus_find_type(unsigned short category, unsigned short type, - const struct nubus_dev *from) +struct nubus_rsrc *nubus_first_rsrc_or_null(void) { - struct nubus_dev *itor = from ? from->next : nubus_devices; - - while (itor) { - if (itor->category == category && itor->type == type) - return itor; - itor = itor->next; - } - return NULL; + return list_first_entry_or_null(&nubus_func_rsrcs, struct nubus_rsrc, + list); } -EXPORT_SYMBOL(nubus_find_type); +EXPORT_SYMBOL(nubus_first_rsrc_or_null); -struct nubus_dev* -nubus_find_slot(unsigned int slot, const struct nubus_dev *from) +struct nubus_rsrc *nubus_next_rsrc_or_null(struct nubus_rsrc *from) { - struct nubus_dev *itor = from ? from->next : nubus_devices; - - while (itor) { - if (itor->board->slot == slot) - return itor; - itor = itor->next; - } - return NULL; + if (list_is_last(&from->list, &nubus_func_rsrcs)) + return NULL; + return list_next_entry(from, list); } -EXPORT_SYMBOL(nubus_find_slot); +EXPORT_SYMBOL(nubus_next_rsrc_or_null); int nubus_find_rsrc(struct nubus_dir *dir, unsigned char rsrc_type, @@ -339,31 +335,83 @@ EXPORT_SYMBOL(nubus_find_rsrc); looking at, and print out lots and lots of information from the resource blocks. */ -/* FIXME: A lot of this stuff will eventually be useful after - initialization, for intelligently probing Ethernet and video chips, - among other things. The rest of it should go in the /proc code. - For now, we just use it to give verbose boot logs. */ +static int __init nubus_get_block_rsrc_dir(struct nubus_board *board, + struct proc_dir_entry *procdir, + const struct nubus_dirent *parent) +{ + struct nubus_dir dir; + struct nubus_dirent ent; + + nubus_get_subdir(parent, &dir); + dir.procdir = nubus_proc_add_rsrc_dir(procdir, parent, board); -static int __init nubus_show_display_resource(struct nubus_dev *dev, - const struct nubus_dirent *ent) + while (nubus_readdir(&dir, &ent) != -1) { + u32 size; + + nubus_get_rsrc_mem(&size, &ent, 4); + pr_debug(" block (0x%x), size %d\n", ent.type, size); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, size); + } + return 0; +} + +static int __init nubus_get_display_vidmode(struct nubus_board *board, + struct proc_dir_entry *procdir, + const struct nubus_dirent *parent) +{ + struct nubus_dir dir; + struct nubus_dirent ent; + + nubus_get_subdir(parent, &dir); + dir.procdir = nubus_proc_add_rsrc_dir(procdir, parent, board); + + while (nubus_readdir(&dir, &ent) != -1) { + switch (ent.type) { + case 1: /* mVidParams */ + case 2: /* mTable */ + { + u32 size; + + nubus_get_rsrc_mem(&size, &ent, 4); + pr_debug(" block (0x%x), size %d\n", ent.type, + size); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, size); + break; + } + default: + pr_debug(" unknown resource 0x%02x, data 0x%06x\n", + ent.type, ent.data); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, 0); + } + } + return 0; +} + +static int __init nubus_get_display_resource(struct nubus_rsrc *fres, + struct proc_dir_entry *procdir, + const struct nubus_dirent *ent) { switch (ent->type) { case NUBUS_RESID_GAMMADIR: - pr_info(" gamma directory offset: 0x%06x\n", ent->data); + pr_debug(" gamma directory offset: 0x%06x\n", ent->data); + nubus_get_block_rsrc_dir(fres->board, procdir, ent); break; case 0x0080 ... 0x0085: - pr_info(" mode %02X info offset: 0x%06x\n", - ent->type, ent->data); + pr_debug(" mode 0x%02x info offset: 0x%06x\n", + ent->type, ent->data); + nubus_get_display_vidmode(fres->board, procdir, ent); break; default: - pr_info(" unknown resource %02X, data 0x%06x\n", - ent->type, ent->data); + pr_debug(" unknown resource 0x%02x, data 0x%06x\n", + ent->type, ent->data); + nubus_proc_add_rsrc_mem(procdir, ent, 0); } return 0; } -static int __init nubus_show_network_resource(struct nubus_dev *dev, - const struct nubus_dirent *ent) +static int __init nubus_get_network_resource(struct nubus_rsrc *fres, + struct proc_dir_entry *procdir, + const struct nubus_dirent *ent) { switch (ent->type) { case NUBUS_RESID_MAC_ADDRESS: @@ -371,18 +419,21 @@ static int __init nubus_show_network_resource(struct nubus_dev *dev, char addr[6]; nubus_get_rsrc_mem(addr, ent, 6); - pr_info(" MAC address: %pM\n", addr); + pr_debug(" MAC address: %pM\n", addr); + nubus_proc_add_rsrc_mem(procdir, ent, 6); break; } default: - pr_info(" unknown resource %02X, data 0x%06x\n", - ent->type, ent->data); + pr_debug(" unknown resource 0x%02x, data 0x%06x\n", + ent->type, ent->data); + nubus_proc_add_rsrc_mem(procdir, ent, 0); } return 0; } -static int __init nubus_show_cpu_resource(struct nubus_dev *dev, - const struct nubus_dirent *ent) +static int __init nubus_get_cpu_resource(struct nubus_rsrc *fres, + struct proc_dir_entry *procdir, + const struct nubus_dirent *ent) { switch (ent->type) { case NUBUS_RESID_MEMINFO: @@ -390,8 +441,9 @@ static int __init nubus_show_cpu_resource(struct nubus_dev *dev, unsigned long meminfo[2]; nubus_get_rsrc_mem(&meminfo, ent, 8); - pr_info(" memory: [ 0x%08lx 0x%08lx ]\n", - meminfo[0], meminfo[1]); + pr_debug(" memory: [ 0x%08lx 0x%08lx ]\n", + meminfo[0], meminfo[1]); + nubus_proc_add_rsrc_mem(procdir, ent, 8); break; } case NUBUS_RESID_ROMINFO: @@ -399,57 +451,60 @@ static int __init nubus_show_cpu_resource(struct nubus_dev *dev, unsigned long rominfo[2]; nubus_get_rsrc_mem(&rominfo, ent, 8); - pr_info(" ROM: [ 0x%08lx 0x%08lx ]\n", - rominfo[0], rominfo[1]); + pr_debug(" ROM: [ 0x%08lx 0x%08lx ]\n", + rominfo[0], rominfo[1]); + nubus_proc_add_rsrc_mem(procdir, ent, 8); break; } default: - pr_info(" unknown resource %02X, data 0x%06x\n", - ent->type, ent->data); + pr_debug(" unknown resource 0x%02x, data 0x%06x\n", + ent->type, ent->data); + nubus_proc_add_rsrc_mem(procdir, ent, 0); } return 0; } -static int __init nubus_show_private_resource(struct nubus_dev *dev, - const struct nubus_dirent *ent) +static int __init nubus_get_private_resource(struct nubus_rsrc *fres, + struct proc_dir_entry *procdir, + const struct nubus_dirent *ent) { - switch (dev->category) { + switch (fres->category) { case NUBUS_CAT_DISPLAY: - nubus_show_display_resource(dev, ent); + nubus_get_display_resource(fres, procdir, ent); break; case NUBUS_CAT_NETWORK: - nubus_show_network_resource(dev, ent); + nubus_get_network_resource(fres, procdir, ent); break; case NUBUS_CAT_CPU: - nubus_show_cpu_resource(dev, ent); + nubus_get_cpu_resource(fres, procdir, ent); break; default: - pr_info(" unknown resource %02X, data 0x%06x\n", - ent->type, ent->data); + pr_debug(" unknown resource 0x%02x, data 0x%06x\n", + ent->type, ent->data); + nubus_proc_add_rsrc_mem(procdir, ent, 0); } return 0; } -static struct nubus_dev * __init +static struct nubus_rsrc * __init nubus_get_functional_resource(struct nubus_board *board, int slot, const struct nubus_dirent *parent) { struct nubus_dir dir; struct nubus_dirent ent; - struct nubus_dev *dev; + struct nubus_rsrc *fres; - pr_info(" Function 0x%02x:\n", parent->type); + pr_debug(" Functional resource 0x%02x:\n", parent->type); nubus_get_subdir(parent, &dir); - - pr_debug("%s: parent is 0x%p, dir is 0x%p\n", - __func__, parent->base, dir.base); + dir.procdir = nubus_proc_add_rsrc_dir(board->procdir, parent, board); /* Actually we should probably panic if this fails */ - if ((dev = kzalloc(sizeof(*dev), GFP_ATOMIC)) == NULL) + fres = kzalloc(sizeof(*fres), GFP_ATOMIC); + if (!fres) return NULL; - dev->resid = parent->type; - dev->directory = dir.base; - dev->board = board; + fres->resid = parent->type; + fres->directory = dir.base; + fres->board = board; while (nubus_readdir(&dir, &ent) != -1) { switch (ent.type) { @@ -458,130 +513,96 @@ nubus_get_functional_resource(struct nubus_board *board, int slot, unsigned short nbtdata[4]; nubus_get_rsrc_mem(nbtdata, &ent, 8); - dev->category = nbtdata[0]; - dev->type = nbtdata[1]; - dev->dr_sw = nbtdata[2]; - dev->dr_hw = nbtdata[3]; - pr_info(" type: [cat 0x%x type 0x%x sw 0x%x hw 0x%x]\n", - nbtdata[0], nbtdata[1], nbtdata[2], nbtdata[3]); + fres->category = nbtdata[0]; + fres->type = nbtdata[1]; + fres->dr_sw = nbtdata[2]; + fres->dr_hw = nbtdata[3]; + pr_debug(" type: [cat 0x%x type 0x%x sw 0x%x hw 0x%x]\n", + nbtdata[0], nbtdata[1], nbtdata[2], nbtdata[3]); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, 8); break; } case NUBUS_RESID_NAME: { - nubus_get_rsrc_str(dev->name, &ent, 64); - pr_info(" name: %s\n", dev->name); + char name[64]; + unsigned int len; + + len = nubus_get_rsrc_str(name, &ent, sizeof(name)); + pr_debug(" name: %s\n", name); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, len + 1); break; } case NUBUS_RESID_DRVRDIR: { /* MacOS driver. If we were NetBSD we might use this :-) */ - struct nubus_dir drvr_dir; - struct nubus_dirent drvr_ent; - - nubus_get_subdir(&ent, &drvr_dir); - nubus_readdir(&drvr_dir, &drvr_ent); - dev->driver = nubus_dirptr(&drvr_ent); - pr_info(" driver at: 0x%p\n", dev->driver); + pr_debug(" driver directory offset: 0x%06x\n", + ent.data); + nubus_get_block_rsrc_dir(board, dir.procdir, &ent); break; } case NUBUS_RESID_MINOR_BASEOS: + { /* We will need this in order to support multiple framebuffers. It might be handy for Ethernet as well */ - nubus_get_rsrc_mem(&dev->iobase, &ent, 4); - pr_info(" memory offset: 0x%08lx\n", dev->iobase); + u32 base_offset; + + nubus_get_rsrc_mem(&base_offset, &ent, 4); + pr_debug(" memory offset: 0x%08x\n", base_offset); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, 4); break; + } case NUBUS_RESID_MINOR_LENGTH: + { /* Ditto */ - nubus_get_rsrc_mem(&dev->iosize, &ent, 4); - pr_info(" memory length: 0x%08lx\n", dev->iosize); + u32 length; + + nubus_get_rsrc_mem(&length, &ent, 4); + pr_debug(" memory length: 0x%08x\n", length); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, 4); break; + } case NUBUS_RESID_FLAGS: - dev->flags = ent.data; - pr_info(" flags: 0x%06x\n", dev->flags); + pr_debug(" flags: 0x%06x\n", ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; case NUBUS_RESID_HWDEVID: - dev->hwdevid = ent.data; - pr_info(" hwdevid: 0x%06x\n", dev->hwdevid); + pr_debug(" hwdevid: 0x%06x\n", ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; default: /* Local/Private resources have their own function */ - nubus_show_private_resource(dev, &ent); + nubus_get_private_resource(fres, dir.procdir, &ent); } } - return dev; -} - -/* This is cool. */ -static int __init nubus_get_vidnames(struct nubus_board *board, - const struct nubus_dirent *parent) -{ - struct nubus_dir dir; - struct nubus_dirent ent; - - /* FIXME: obviously we want to put this in a header file soon */ - struct vidmode { - u32 size; - /* Don't know what this is yet */ - u16 id; - /* Longest one I've seen so far is 26 characters */ - char name[32]; - }; - - pr_info(" video modes supported:\n"); - nubus_get_subdir(parent, &dir); - pr_debug("%s: parent is 0x%p, dir is 0x%p\n", - __func__, parent->base, dir.base); - - while (nubus_readdir(&dir, &ent) != -1) { - struct vidmode mode; - u32 size; - - /* First get the length */ - nubus_get_rsrc_mem(&size, &ent, 4); - - /* Now clobber the whole thing */ - if (size > sizeof(mode) - 1) - size = sizeof(mode) - 1; - memset(&mode, 0, sizeof(mode)); - nubus_get_rsrc_mem(&mode, &ent, size); - pr_info(" %02X: (%02X) %s\n", ent.type, - mode.id, mode.name); - } - return 0; + return fres; } /* This is *really* cool. */ static int __init nubus_get_icon(struct nubus_board *board, + struct proc_dir_entry *procdir, const struct nubus_dirent *ent) { /* Should be 32x32 if my memory serves me correctly */ - unsigned char icon[128]; - int x, y; + u32 icon[32]; + int i; nubus_get_rsrc_mem(&icon, ent, 128); - pr_info(" icon:\n"); - - /* We should actually plot these somewhere in the framebuffer - init. This is just to demonstrate that they do, in fact, - exist */ - for (y = 0; y < 32; y++) { - pr_info(" "); - for (x = 0; x < 32; x++) { - if (icon[y * 4 + x / 8] & (0x80 >> (x % 8))) - pr_cont("*"); - else - pr_cont(" "); - } - pr_cont("\n"); - } + pr_debug(" icon:\n"); + for (i = 0; i < 8; i++) + pr_debug(" %08x %08x %08x %08x\n", + icon[i * 4 + 0], icon[i * 4 + 1], + icon[i * 4 + 2], icon[i * 4 + 3]); + nubus_proc_add_rsrc_mem(procdir, ent, 128); + return 0; } static int __init nubus_get_vendorinfo(struct nubus_board *board, + struct proc_dir_entry *procdir, const struct nubus_dirent *parent) { struct nubus_dir dir; @@ -589,19 +610,20 @@ static int __init nubus_get_vendorinfo(struct nubus_board *board, static char *vendor_fields[6] = { "ID", "serial", "revision", "part", "date", "unknown field" }; - pr_info(" vendor info:\n"); + pr_debug(" vendor info:\n"); nubus_get_subdir(parent, &dir); - pr_debug("%s: parent is 0x%p, dir is 0x%p\n", - __func__, parent->base, dir.base); + dir.procdir = nubus_proc_add_rsrc_dir(procdir, parent, board); while (nubus_readdir(&dir, &ent) != -1) { char name[64]; + unsigned int len; /* These are all strings, we think */ - nubus_get_rsrc_str(name, &ent, 64); - if (ent.type > 5) + len = nubus_get_rsrc_str(name, &ent, sizeof(name)); + if (ent.type < 1 || ent.type > 5) ent.type = 5; - pr_info(" %s: %s\n", vendor_fields[ent.type - 1], name); + pr_debug(" %s: %s\n", vendor_fields[ent.type - 1], name); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, len + 1); } return 0; } @@ -612,9 +634,9 @@ static int __init nubus_get_board_resource(struct nubus_board *board, int slot, struct nubus_dir dir; struct nubus_dirent ent; + pr_debug(" Board resource 0x%02x:\n", parent->type); nubus_get_subdir(parent, &dir); - pr_debug("%s: parent is 0x%p, dir is 0x%p\n", - __func__, parent->base, dir.base); + dir.procdir = nubus_proc_add_rsrc_dir(board->procdir, parent, board); while (nubus_readdir(&dir, &ent) != -1) { switch (ent.type) { @@ -625,64 +647,81 @@ static int __init nubus_get_board_resource(struct nubus_board *board, int slot, useful except insofar as it tells us that we really are looking at a board resource. */ nubus_get_rsrc_mem(nbtdata, &ent, 8); - pr_info(" type: [cat 0x%x type 0x%x sw 0x%x hw 0x%x]\n", - nbtdata[0], nbtdata[1], nbtdata[2], nbtdata[3]); + pr_debug(" type: [cat 0x%x type 0x%x sw 0x%x hw 0x%x]\n", + nbtdata[0], nbtdata[1], nbtdata[2], nbtdata[3]); if (nbtdata[0] != 1 || nbtdata[1] != 0 || nbtdata[2] != 0 || nbtdata[3] != 0) - pr_err("this sResource is not a board resource!\n"); + pr_err("Slot %X: sResource is not a board resource!\n", + slot); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, 8); break; } case NUBUS_RESID_NAME: - nubus_get_rsrc_str(board->name, &ent, 64); - pr_info(" name: %s\n", board->name); + { + unsigned int len; + + len = nubus_get_rsrc_str(board->name, &ent, + sizeof(board->name)); + pr_debug(" name: %s\n", board->name); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, len + 1); break; + } case NUBUS_RESID_ICON: - nubus_get_icon(board, &ent); + nubus_get_icon(board, dir.procdir, &ent); break; case NUBUS_RESID_BOARDID: - pr_info(" board id: 0x%x\n", ent.data); + pr_debug(" board id: 0x%x\n", ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; case NUBUS_RESID_PRIMARYINIT: - pr_info(" primary init offset: 0x%06x\n", ent.data); + pr_debug(" primary init offset: 0x%06x\n", ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; case NUBUS_RESID_VENDORINFO: - nubus_get_vendorinfo(board, &ent); + nubus_get_vendorinfo(board, dir.procdir, &ent); break; case NUBUS_RESID_FLAGS: - pr_info(" flags: 0x%06x\n", ent.data); + pr_debug(" flags: 0x%06x\n", ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; case NUBUS_RESID_HWDEVID: - pr_info(" hwdevid: 0x%06x\n", ent.data); + pr_debug(" hwdevid: 0x%06x\n", ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; case NUBUS_RESID_SECONDINIT: - pr_info(" secondary init offset: 0x%06x\n", ent.data); + pr_debug(" secondary init offset: 0x%06x\n", + ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; /* WTF isn't this in the functional resources? */ case NUBUS_RESID_VIDNAMES: - nubus_get_vidnames(board, &ent); + pr_debug(" vidnames directory offset: 0x%06x\n", + ent.data); + nubus_get_block_rsrc_dir(board, dir.procdir, &ent); break; /* Same goes for this */ case NUBUS_RESID_VIDMODES: - pr_info(" video mode parameter directory offset: 0x%06x\n", - ent.data); + pr_debug(" video mode parameter directory offset: 0x%06x\n", + ent.data); + nubus_proc_add_rsrc(dir.procdir, &ent); break; default: - pr_info(" unknown resource %02X, data 0x%06x\n", - ent.type, ent.data); + pr_debug(" unknown resource 0x%02x, data 0x%06x\n", + ent.type, ent.data); + nubus_proc_add_rsrc_mem(dir.procdir, &ent, 0); } } return 0; } -/* Add a board (might be many devices) to the list */ -static struct nubus_board * __init nubus_add_board(int slot, int bytelanes) +static void __init nubus_add_board(int slot, int bytelanes) { struct nubus_board *board; - struct nubus_board **boardp; unsigned char *rp; unsigned long dpat; struct nubus_dir dir; struct nubus_dirent ent; + int prev_resid = -1; /* Move to the start of the format block */ rp = nubus_rom_addr(slot); @@ -690,19 +729,19 @@ static struct nubus_board * __init nubus_add_board(int slot, int bytelanes) /* Actually we should probably panic if this fails */ if ((board = kzalloc(sizeof(*board), GFP_ATOMIC)) == NULL) - return NULL; + return; board->fblock = rp; /* Dump the format block for debugging purposes */ pr_debug("Slot %X, format block at 0x%p:\n", slot, rp); + pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); + pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); + pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); pr_debug("%02lx\n", nubus_get_rom(&rp, 1, bytelanes)); pr_debug("%02lx\n", nubus_get_rom(&rp, 1, bytelanes)); pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); pr_debug("%02lx\n", nubus_get_rom(&rp, 1, bytelanes)); pr_debug("%02lx\n", nubus_get_rom(&rp, 1, bytelanes)); - pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); - pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); - pr_debug("%08lx\n", nubus_get_rom(&rp, 4, bytelanes)); rp = board->fblock; board->slot = slot; @@ -722,10 +761,10 @@ static struct nubus_board * __init nubus_add_board(int slot, int bytelanes) /* Directory offset should be small and negative... */ if (!(board->doffset & 0x00FF0000)) - pr_warn("Dodgy doffset!\n"); + pr_warn("Slot %X: Dodgy doffset!\n", slot); dpat = nubus_get_rom(&rp, 4, bytelanes); if (dpat != NUBUS_TEST_PATTERN) - pr_warn("Wrong test pattern %08lx!\n", dpat); + pr_warn("Slot %X: Wrong test pattern %08lx!\n", slot, dpat); /* * I wonder how the CRC is meant to work - @@ -742,53 +781,52 @@ static struct nubus_board * __init nubus_add_board(int slot, int bytelanes) nubus_get_root_dir(board, &dir); /* We're ready to rock */ - pr_info("Slot %X:\n", slot); + pr_debug("Slot %X resources:\n", slot); /* Each slot should have one board resource and any number of - functional resources. So we'll fill in some fields in the - struct nubus_board from the board resource, then walk down - the list of functional resources, spinning out a nubus_dev - for each of them. */ + * functional resources. So we'll fill in some fields in the + * struct nubus_board from the board resource, then walk down + * the list of functional resources, spinning out a nubus_rsrc + * for each of them. + */ if (nubus_readdir(&dir, &ent) == -1) { /* We can't have this! */ - pr_err("Board resource not found!\n"); - return NULL; - } else { - pr_info(" Board resource:\n"); - nubus_get_board_resource(board, slot, &ent); + pr_err("Slot %X: Board resource not found!\n", slot); + kfree(board); + return; } + if (ent.type < 1 || ent.type > 127) + pr_warn("Slot %X: Board resource ID is invalid!\n", slot); + + board->procdir = nubus_proc_add_board(board); + + nubus_get_board_resource(board, slot, &ent); + while (nubus_readdir(&dir, &ent) != -1) { - struct nubus_dev *dev; - struct nubus_dev **devp; + struct nubus_rsrc *fres; - dev = nubus_get_functional_resource(board, slot, &ent); - if (dev == NULL) + fres = nubus_get_functional_resource(board, slot, &ent); + if (fres == NULL) continue; - /* We zeroed this out above */ - if (board->first_dev == NULL) - board->first_dev = dev; + /* Resources should appear in ascending ID order. This sanity + * check prevents duplicate resource IDs. + */ + if (fres->resid <= prev_resid) { + kfree(fres); + continue; + } + prev_resid = fres->resid; - /* Put it on the global NuBus device chain. Keep entries in order. */ - for (devp = &nubus_devices; *devp != NULL; - devp = &((*devp)->next)) - /* spin */; - *devp = dev; - dev->next = NULL; + list_add_tail(&fres->list, &nubus_func_rsrcs); } - /* Put it on the global NuBus board chain. Keep entries in order. */ - for (boardp = &nubus_boards; *boardp != NULL; - boardp = &((*boardp)->next)) - /* spin */; - *boardp = board; - board->next = NULL; - - return board; + if (nubus_device_register(board)) + put_device(&board->dev); } -void __init nubus_probe_slot(int slot) +static void __init nubus_probe_slot(int slot) { unsigned char dp; unsigned char *rp; @@ -796,11 +834,8 @@ void __init nubus_probe_slot(int slot) rp = nubus_rom_addr(slot); for (i = 4; i; i--) { - int card_present; - rp--; - card_present = hwreg_present(rp); - if (!card_present) + if (!hwreg_present(rp)) continue; dp = *rp; @@ -822,10 +857,11 @@ void __init nubus_probe_slot(int slot) } } -void __init nubus_scan_bus(void) +static void __init nubus_scan_bus(void) { int slot; + pr_info("NuBus: Scanning NuBus slots.\n"); for (slot = 9; slot < 15; slot++) { nubus_probe_slot(slot); } @@ -833,14 +869,16 @@ void __init nubus_scan_bus(void) static int __init nubus_init(void) { + int err; + if (!MACH_IS_MAC) return 0; - pr_info("NuBus: Scanning NuBus slots.\n"); - nubus_devices = NULL; - nubus_boards = NULL; - nubus_scan_bus(); nubus_proc_init(); + err = nubus_bus_register(); + if (err) + return err; + nubus_scan_bus(); return 0; } diff --git a/drivers/nubus/proc.c b/drivers/nubus/proc.c index 004a122ac0ff..c2e5a7e6bd3e 100644 --- a/drivers/nubus/proc.c +++ b/drivers/nubus/proc.c @@ -11,39 +11,37 @@ structure in /proc analogous to the structure of the NuBus ROM resources. - Therefore each NuBus device is in fact a directory, which may in - turn contain subdirectories. The "files" correspond to NuBus - resource records. For those types of records which we know how to - convert to formats that are meaningful to userspace (mostly just - icons) these files will provide "cooked" data. Otherwise they will - simply provide raw access (read-only of course) to the ROM. */ + Therefore each board function gets a directory, which may in turn + contain subdirectories. Each slot resource is a file. Unrecognized + resources are empty files, since every resource ID requires a special + case (e.g. if the resource ID implies a directory or block, then its + value has to be interpreted as a slot ROM pointer etc.). + */ #include <linux/types.h> #include <linux/kernel.h> #include <linux/nubus.h> #include <linux/proc_fs.h> #include <linux/seq_file.h> +#include <linux/slab.h> #include <linux/init.h> #include <linux/module.h> - #include <linux/uaccess.h> #include <asm/byteorder.h> +/* + * /proc/bus/nubus/devices stuff + */ + static int nubus_devices_proc_show(struct seq_file *m, void *v) { - struct nubus_dev *dev = nubus_devices; - - while (dev) { - seq_printf(m, "%x\t%04x %04x %04x %04x", - dev->board->slot, - dev->category, - dev->type, - dev->dr_sw, - dev->dr_hw); - seq_printf(m, "\t%08lx\n", dev->board->slot_addr); - dev = dev->next; - } + struct nubus_rsrc *fres; + + for_each_func_rsrc(fres) + seq_printf(m, "%x\t%04x %04x %04x %04x\t%08lx\n", + fres->board->slot, fres->category, fres->type, + fres->dr_sw, fres->dr_hw, fres->board->slot_addr); return 0; } @@ -61,174 +59,163 @@ static const struct file_operations nubus_devices_proc_fops = { static struct proc_dir_entry *proc_bus_nubus_dir; -static const struct file_operations nubus_proc_subdir_fops = { -#warning Need to set some I/O handlers here -}; +/* + * /proc/bus/nubus/x/ stuff + */ -static void nubus_proc_subdir(struct nubus_dev* dev, - struct proc_dir_entry* parent, - struct nubus_dir* dir) +struct proc_dir_entry *nubus_proc_add_board(struct nubus_board *board) { - struct nubus_dirent ent; - - /* Some of these are directories, others aren't */ - while (nubus_readdir(dir, &ent) != -1) { - char name[8]; - struct proc_dir_entry* e; - - sprintf(name, "%x", ent.type); - e = proc_create(name, S_IFREG | S_IRUGO | S_IWUSR, parent, - &nubus_proc_subdir_fops); - if (!e) - return; - } + char name[2]; + + if (!proc_bus_nubus_dir) + return NULL; + snprintf(name, sizeof(name), "%x", board->slot); + return proc_mkdir(name, proc_bus_nubus_dir); } -/* Can't do this recursively since the root directory is structured - somewhat differently from the subdirectories */ -static void nubus_proc_populate(struct nubus_dev* dev, - struct proc_dir_entry* parent, - struct nubus_dir* root) +/* The PDE private data for any directory under /proc/bus/nubus/x/ + * is the bytelanes value for the board in slot x. + */ + +struct proc_dir_entry *nubus_proc_add_rsrc_dir(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent, + struct nubus_board *board) { - struct nubus_dirent ent; - - /* We know these are all directories (board resource + one or - more functional resources) */ - while (nubus_readdir(root, &ent) != -1) { - char name[8]; - struct proc_dir_entry* e; - struct nubus_dir dir; - - sprintf(name, "%x", ent.type); - e = proc_mkdir(name, parent); - if (!e) return; - - /* And descend */ - if (nubus_get_subdir(&ent, &dir) == -1) { - /* This shouldn't happen */ - printk(KERN_ERR "NuBus root directory node %x:%x has no subdir!\n", - dev->board->slot, ent.type); - continue; - } else { - nubus_proc_subdir(dev, e, &dir); - } - } + char name[9]; + int lanes = board->lanes; + + if (!procdir) + return NULL; + snprintf(name, sizeof(name), "%x", ent->type); + return proc_mkdir_data(name, 0555, procdir, (void *)lanes); } -int nubus_proc_attach_device(struct nubus_dev *dev) +/* The PDE private data for a file under /proc/bus/nubus/x/ is a pointer to + * an instance of the following structure, which gives the location and size + * of the resource data in the slot ROM. For slot resources which hold only a + * small integer, this integer value is stored directly and size is set to 0. + * A NULL private data pointer indicates an unrecognized resource. + */ + +struct nubus_proc_pde_data { + unsigned char *res_ptr; + unsigned int res_size; +}; + +static struct nubus_proc_pde_data * +nubus_proc_alloc_pde_data(unsigned char *ptr, unsigned int size) { - struct proc_dir_entry *e; - struct nubus_dir root; - char name[8]; - - if (dev == NULL) { - printk(KERN_ERR - "NULL pointer in nubus_proc_attach_device, shoot the programmer!\n"); - return -1; - } - - if (dev->board == NULL) { - printk(KERN_ERR - "NULL pointer in nubus_proc_attach_device, shoot the programmer!\n"); - printk("dev = %p, dev->board = %p\n", dev, dev->board); - return -1; - } - - /* Create a directory */ - sprintf(name, "%x", dev->board->slot); - e = dev->procdir = proc_mkdir(name, proc_bus_nubus_dir); - if (!e) - return -ENOMEM; + struct nubus_proc_pde_data *pde_data; - /* Now recursively populate it with files */ - nubus_get_root_dir(dev->board, &root); - nubus_proc_populate(dev, e, &root); + pde_data = kmalloc(sizeof(*pde_data), GFP_KERNEL); + if (!pde_data) + return NULL; - return 0; + pde_data->res_ptr = ptr; + pde_data->res_size = size; + return pde_data; } -EXPORT_SYMBOL(nubus_proc_attach_device); -/* - * /proc/nubus stuff - */ -static int nubus_proc_show(struct seq_file *m, void *v) +static int nubus_proc_rsrc_show(struct seq_file *m, void *v) { - const struct nubus_board *board = v; + struct inode *inode = m->private; + struct nubus_proc_pde_data *pde_data; - /* Display header on line 1 */ - if (v == SEQ_START_TOKEN) - seq_puts(m, "Nubus devices found:\n"); - else - seq_printf(m, "Slot %X: %s\n", board->slot, board->name); + pde_data = PDE_DATA(inode); + if (!pde_data) + return 0; + + if (pde_data->res_size > m->size) + return -EFBIG; + + if (pde_data->res_size) { + int lanes = (int)proc_get_parent_data(inode); + struct nubus_dirent ent; + + if (!lanes) + return 0; + + ent.mask = lanes; + ent.base = pde_data->res_ptr; + ent.data = 0; + nubus_seq_write_rsrc_mem(m, &ent, pde_data->res_size); + } else { + unsigned int data = (unsigned int)pde_data->res_ptr; + + seq_putc(m, data >> 16); + seq_putc(m, data >> 8); + seq_putc(m, data >> 0); + } return 0; } -static void *nubus_proc_start(struct seq_file *m, loff_t *_pos) +static int nubus_proc_rsrc_open(struct inode *inode, struct file *file) { - struct nubus_board *board; - unsigned pos; - - if (*_pos > LONG_MAX) - return NULL; - pos = *_pos; - if (pos == 0) - return SEQ_START_TOKEN; - for (board = nubus_boards; board; board = board->next) - if (--pos == 0) - break; - return board; + return single_open(file, nubus_proc_rsrc_show, inode); } -static void *nubus_proc_next(struct seq_file *p, void *v, loff_t *_pos) +static const struct file_operations nubus_proc_rsrc_fops = { + .open = nubus_proc_rsrc_open, + .read = seq_read, + .llseek = seq_lseek, + .release = single_release, +}; + +void nubus_proc_add_rsrc_mem(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent, + unsigned int size) { - /* Walk the list of NuBus boards */ - struct nubus_board *board = v; - - ++*_pos; - if (v == SEQ_START_TOKEN) - board = nubus_boards; - else if (board) - board = board->next; - return board; + char name[9]; + struct nubus_proc_pde_data *pde_data; + + if (!procdir) + return; + + snprintf(name, sizeof(name), "%x", ent->type); + if (size) + pde_data = nubus_proc_alloc_pde_data(nubus_dirptr(ent), size); + else + pde_data = NULL; + proc_create_data(name, S_IFREG | 0444, procdir, + &nubus_proc_rsrc_fops, pde_data); } -static void nubus_proc_stop(struct seq_file *p, void *v) +void nubus_proc_add_rsrc(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent) { + char name[9]; + unsigned char *data = (unsigned char *)ent->data; + + if (!procdir) + return; + + snprintf(name, sizeof(name), "%x", ent->type); + proc_create_data(name, S_IFREG | 0444, procdir, + &nubus_proc_rsrc_fops, + nubus_proc_alloc_pde_data(data, 0)); } -static const struct seq_operations nubus_proc_seqops = { - .start = nubus_proc_start, - .next = nubus_proc_next, - .stop = nubus_proc_stop, - .show = nubus_proc_show, -}; +/* + * /proc/nubus stuff + */ static int nubus_proc_open(struct inode *inode, struct file *file) { - return seq_open(file, &nubus_proc_seqops); + return single_open(file, nubus_proc_show, NULL); } static const struct file_operations nubus_proc_fops = { .open = nubus_proc_open, .read = seq_read, .llseek = seq_lseek, - .release = seq_release, + .release = single_release, }; -void __init proc_bus_nubus_add_devices(void) -{ - struct nubus_dev *dev; - - for(dev = nubus_devices; dev; dev = dev->next) - nubus_proc_attach_device(dev); -} - void __init nubus_proc_init(void) { proc_create("nubus", 0, NULL, &nubus_proc_fops); - if (!MACH_IS_MAC) - return; proc_bus_nubus_dir = proc_mkdir("bus/nubus", NULL); + if (!proc_bus_nubus_dir) + return; proc_create("devices", 0, proc_bus_nubus_dir, &nubus_devices_proc_fops); - proc_bus_nubus_add_devices(); } diff --git a/drivers/video/fbdev/macfb.c b/drivers/video/fbdev/macfb.c index cda7587cbc86..e707e617bf1c 100644 --- a/drivers/video/fbdev/macfb.c +++ b/drivers/video/fbdev/macfb.c @@ -556,7 +556,7 @@ static void __init iounmap_macfb(void) static int __init macfb_init(void) { int video_cmap_len, video_is_nubus = 0; - struct nubus_dev* ndev = NULL; + struct nubus_rsrc *ndev = NULL; char *option = NULL; int err; @@ -670,15 +670,17 @@ static int __init macfb_init(void) * code is really broken :-) */ - while ((ndev = nubus_find_type(NUBUS_CAT_DISPLAY, - NUBUS_TYPE_VIDEO, ndev))) - { + for_each_func_rsrc(ndev) { unsigned long base = ndev->board->slot_addr; if (mac_bi_data.videoaddr < base || mac_bi_data.videoaddr - base > 0xFFFFFF) continue; + if (ndev->category != NUBUS_CAT_DISPLAY || + ndev->type != NUBUS_TYPE_VIDEO) + continue; + video_is_nubus = 1; slot_addr = (unsigned char *)base; diff --git a/include/linux/nubus.h b/include/linux/nubus.h index 11ce6b1117a8..6e8200215321 100644 --- a/include/linux/nubus.h +++ b/include/linux/nubus.h @@ -5,20 +5,36 @@ Originally written by Alan Cox. Hacked to death by C. Scott Ananian and David Huggins-Daines. - - Some of the constants in here are from the corresponding - NetBSD/OpenBSD header file, by Allen Briggs. We figured out the - rest of them on our own. */ +*/ + #ifndef LINUX_NUBUS_H #define LINUX_NUBUS_H +#include <linux/device.h> #include <asm/nubus.h> #include <uapi/linux/nubus.h> +struct proc_dir_entry; +struct seq_file; + +struct nubus_dir { + unsigned char *base; + unsigned char *ptr; + int done; + int mask; + struct proc_dir_entry *procdir; +}; + +struct nubus_dirent { + unsigned char *base; + unsigned char type; + __u32 data; /* Actually 24 bits used */ + int mask; +}; + struct nubus_board { - struct nubus_board* next; - struct nubus_dev* first_dev; - + struct device dev; + /* Only 9-E actually exist, though 0-8 are also theoretically possible, and 0 is a special case which represents the motherboard and onboard peripherals (Ethernet, video) */ @@ -27,10 +43,10 @@ struct nubus_board { char name[64]; /* Format block */ - unsigned char* fblock; + unsigned char *fblock; /* Root directory (does *not* always equal fblock + doffset!) */ - unsigned char* directory; - + unsigned char *directory; + unsigned long slot_addr; /* Offset to root directory (sometimes) */ unsigned long doffset; @@ -41,15 +57,15 @@ struct nubus_board { unsigned char rev; unsigned char format; unsigned char lanes; -}; -struct nubus_dev { - /* Next link in device list */ - struct nubus_dev* next; /* Directory entry in /proc/bus/nubus */ - struct proc_dir_entry* procdir; + struct proc_dir_entry *procdir; +}; + +struct nubus_rsrc { + struct list_head list; - /* The functional resource ID of this device */ + /* The functional resource ID */ unsigned char resid; /* These are mostly here for convenience; we could always read them from the ROMs if we wanted to */ @@ -57,79 +73,116 @@ struct nubus_dev { unsigned short type; unsigned short dr_sw; unsigned short dr_hw; - /* This is the device's name rather than the board's. - Sometimes they are different. Usually the board name is - more correct. */ - char name[64]; - /* MacOS driver (I kid you not) */ - unsigned char* driver; - /* Actually this is an offset */ - unsigned long iobase; - unsigned long iosize; - unsigned char flags, hwdevid; - + /* Functional directory */ - unsigned char* directory; + unsigned char *directory; /* Much of our info comes from here */ - struct nubus_board* board; + struct nubus_board *board; +}; + +/* This is all NuBus functional resources (used to find devices later on) */ +extern struct list_head nubus_func_rsrcs; + +struct nubus_driver { + struct device_driver driver; + int (*probe)(struct nubus_board *board); + int (*remove)(struct nubus_board *board); }; -/* This is all NuBus devices (used to find devices later on) */ -extern struct nubus_dev* nubus_devices; -/* This is all NuBus cards */ -extern struct nubus_board* nubus_boards; +extern struct bus_type nubus_bus_type; /* Generic NuBus interface functions, modelled after the PCI interface */ -void nubus_scan_bus(void); #ifdef CONFIG_PROC_FS -extern void nubus_proc_init(void); +void nubus_proc_init(void); +struct proc_dir_entry *nubus_proc_add_board(struct nubus_board *board); +struct proc_dir_entry *nubus_proc_add_rsrc_dir(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent, + struct nubus_board *board); +void nubus_proc_add_rsrc_mem(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent, + unsigned int size); +void nubus_proc_add_rsrc(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent); #else static inline void nubus_proc_init(void) {} +static inline +struct proc_dir_entry *nubus_proc_add_board(struct nubus_board *board) +{ return NULL; } +static inline +struct proc_dir_entry *nubus_proc_add_rsrc_dir(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent, + struct nubus_board *board) +{ return NULL; } +static inline void nubus_proc_add_rsrc_mem(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent, + unsigned int size) {} +static inline void nubus_proc_add_rsrc(struct proc_dir_entry *procdir, + const struct nubus_dirent *ent) {} #endif -int get_nubus_list(char *buf); -int nubus_proc_attach_device(struct nubus_dev *dev); -/* If we need more precision we can add some more of these */ -struct nubus_dev* nubus_find_device(unsigned short category, - unsigned short type, - unsigned short dr_hw, - unsigned short dr_sw, - const struct nubus_dev* from); -struct nubus_dev* nubus_find_type(unsigned short category, - unsigned short type, - const struct nubus_dev* from); -/* Might have more than one device in a slot, you know... */ -struct nubus_dev* nubus_find_slot(unsigned int slot, - const struct nubus_dev* from); + +struct nubus_rsrc *nubus_first_rsrc_or_null(void); +struct nubus_rsrc *nubus_next_rsrc_or_null(struct nubus_rsrc *from); + +#define for_each_func_rsrc(f) \ + for (f = nubus_first_rsrc_or_null(); f; f = nubus_next_rsrc_or_null(f)) + +#define for_each_board_func_rsrc(b, f) \ + for_each_func_rsrc(f) if (f->board != b) {} else /* These are somewhat more NuBus-specific. They all return 0 for success and -1 for failure, as you'd expect. */ /* The root directory which contains the board and functional directories */ -int nubus_get_root_dir(const struct nubus_board* board, - struct nubus_dir* dir); +int nubus_get_root_dir(const struct nubus_board *board, + struct nubus_dir *dir); /* The board directory */ -int nubus_get_board_dir(const struct nubus_board* board, - struct nubus_dir* dir); +int nubus_get_board_dir(const struct nubus_board *board, + struct nubus_dir *dir); /* The functional directory */ -int nubus_get_func_dir(const struct nubus_dev* dev, - struct nubus_dir* dir); +int nubus_get_func_dir(const struct nubus_rsrc *fres, struct nubus_dir *dir); /* These work on any directory gotten via the above */ -int nubus_readdir(struct nubus_dir* dir, - struct nubus_dirent* ent); -int nubus_find_rsrc(struct nubus_dir* dir, +int nubus_readdir(struct nubus_dir *dir, + struct nubus_dirent *ent); +int nubus_find_rsrc(struct nubus_dir *dir, unsigned char rsrc_type, - struct nubus_dirent* ent); -int nubus_rewinddir(struct nubus_dir* dir); + struct nubus_dirent *ent); +int nubus_rewinddir(struct nubus_dir *dir); /* Things to do with directory entries */ -int nubus_get_subdir(const struct nubus_dirent* ent, - struct nubus_dir* dir); -void nubus_get_rsrc_mem(void* dest, - const struct nubus_dirent *dirent, - int len); -void nubus_get_rsrc_str(void* dest, - const struct nubus_dirent *dirent, - int maxlen); +int nubus_get_subdir(const struct nubus_dirent *ent, + struct nubus_dir *dir); +void nubus_get_rsrc_mem(void *dest, const struct nubus_dirent *dirent, + unsigned int len); +unsigned int nubus_get_rsrc_str(char *dest, const struct nubus_dirent *dirent, + unsigned int len); +void nubus_seq_write_rsrc_mem(struct seq_file *m, + const struct nubus_dirent *dirent, + unsigned int len); +unsigned char *nubus_dirptr(const struct nubus_dirent *nd); + +/* Declarations relating to driver model objects */ +int nubus_bus_register(void); +int nubus_device_register(struct nubus_board *board); +int nubus_driver_register(struct nubus_driver *ndrv); +void nubus_driver_unregister(struct nubus_driver *ndrv); +int nubus_proc_show(struct seq_file *m, void *data); + +static inline void nubus_set_drvdata(struct nubus_board *board, void *data) +{ + dev_set_drvdata(&board->dev, data); +} + +static inline void *nubus_get_drvdata(struct nubus_board *board) +{ + return dev_get_drvdata(&board->dev); +} + +/* Returns a pointer to the "standard" slot space. */ +static inline void *nubus_slot_addr(int slot) +{ + return (void *)(0xF0000000 | (slot << 24)); +} + #endif /* LINUX_NUBUS_H */ diff --git a/include/uapi/linux/nubus.h b/include/uapi/linux/nubus.h index f3776cc80f4d..48031e7858f1 100644 --- a/include/uapi/linux/nubus.h +++ b/include/uapi/linux/nubus.h @@ -221,27 +221,4 @@ enum nubus_display_res_id { NUBUS_RESID_SIXTHMODE = 0x0085 }; -struct nubus_dir -{ - unsigned char *base; - unsigned char *ptr; - int done; - int mask; -}; - -struct nubus_dirent -{ - unsigned char *base; - unsigned char type; - __u32 data; /* Actually 24bits used */ - int mask; -}; - - -/* We'd like to get rid of this eventually. Only daynaport.c uses it now. */ -static inline void *nubus_slot_addr(int slot) -{ - return (void *)(0xF0000000|(slot<<24)); -} - #endif /* _UAPILINUX_NUBUS_H */ |