// SPDX-License-Identifier: GPL-2.0
/*
 *	linux/arch/alpha/kernel/sys_eiger.c
 *
 *	Copyright (C) 1995 David A Rusling
 *	Copyright (C) 1996, 1999 Jay A Estabrook
 *	Copyright (C) 1998, 1999 Richard Henderson
 *	Copyright (C) 1999 Iain Grant
 *
 * Code supporting the EIGER (EV6+TSUNAMI).
 */

#include <linux/kernel.h>
#include <linux/types.h>
#include <linux/mm.h>
#include <linux/sched.h>
#include <linux/pci.h>
#include <linux/init.h>
#include <linux/bitops.h>

#include <asm/ptrace.h>
#include <asm/dma.h>
#include <asm/irq.h>
#include <asm/mmu_context.h>
#include <asm/io.h>
#include <asm/pgtable.h>
#include <asm/core_tsunami.h>
#include <asm/hwrpb.h>
#include <asm/tlbflush.h>

#include "proto.h"
#include "irq_impl.h"
#include "pci_impl.h"
#include "machvec_impl.h"


/* Note that this interrupt code is identical to TAKARA.  */

/* Note mask bit is true for DISABLED irqs.  */
static unsigned long cached_irq_mask[2] = { -1, -1 };

static inline void
eiger_update_irq_hw(unsigned long irq, unsigned long mask)
{
	int regaddr;

	mask = (irq >= 64 ? mask << 16 : mask >> ((irq - 16) & 0x30));
	regaddr = 0x510 + (((irq - 16) >> 2) & 0x0c);
	outl(mask & 0xffff0000UL, regaddr);
}

static inline void
eiger_enable_irq(struct irq_data *d)
{
	unsigned int irq = d->irq;
	unsigned long mask;
	mask = (cached_irq_mask[irq >= 64] &= ~(1UL << (irq & 63)));
	eiger_update_irq_hw(irq, mask);
}

static void
eiger_disable_irq(struct irq_data *d)
{
	unsigned int irq = d->irq;
	unsigned long mask;
	mask = (cached_irq_mask[irq >= 64] |= 1UL << (irq & 63));
	eiger_update_irq_hw(irq, mask);
}

static struct irq_chip eiger_irq_type = {
	.name		= "EIGER",
	.irq_unmask	= eiger_enable_irq,
	.irq_mask	= eiger_disable_irq,
	.irq_mask_ack	= eiger_disable_irq,
};

static void
eiger_device_interrupt(unsigned long vector)
{
	unsigned intstatus;

	/*
	 * The PALcode will have passed us vectors 0x800 or 0x810,
	 * which are fairly arbitrary values and serve only to tell
	 * us whether an interrupt has come in on IRQ0 or IRQ1. If
	 * it's IRQ1 it's a PCI interrupt; if it's IRQ0, it's
	 * probably ISA, but PCI interrupts can come through IRQ0
	 * as well if the interrupt controller isn't in accelerated
	 * mode.
	 *
	 * OTOH, the accelerator thing doesn't seem to be working
	 * overly well, so what we'll do instead is try directly
	 * examining the Master Interrupt Register to see if it's a
	 * PCI interrupt, and if _not_ then we'll pass it on to the
	 * ISA handler.
	 */

	intstatus = inw(0x500) & 15;
	if (intstatus) {
		/*
		 * This is a PCI interrupt. Check each bit and
		 * despatch an interrupt if it's set.
		 */

		if (intstatus & 8) handle_irq(16+3);
		if (intstatus & 4) handle_irq(16+2);
		if (intstatus & 2) handle_irq(16+1);
		if (intstatus & 1) handle_irq(16+0);
	} else {
		isa_device_interrupt(vector);
	}
}

static void
eiger_srm_device_interrupt(unsigned long vector)
{
	int irq = (vector - 0x800) >> 4;
	handle_irq(irq);
}

static void __init
eiger_init_irq(void)
{
	long i;

	outb(0, DMA1_RESET_REG);
	outb(0, DMA2_RESET_REG);
	outb(DMA_MODE_CASCADE, DMA2_MODE_REG);
	outb(0, DMA2_MASK_REG);

	if (alpha_using_srm)
		alpha_mv.device_interrupt = eiger_srm_device_interrupt;

	for (i = 16; i < 128; i += 16)
		eiger_update_irq_hw(i, -1);

	init_i8259a_irqs();

	for (i = 16; i < 128; ++i) {
		irq_set_chip_and_handler(i, &eiger_irq_type, handle_level_irq);
		irq_set_status_flags(i, IRQ_LEVEL);
	}
}

static int
eiger_map_irq(const struct pci_dev *dev, u8 slot, u8 pin)
{
	u8 irq_orig;

	/* The SRM console has already calculated out the IRQ value's for
	   option cards. As this works lets just read in the value already
	   set and change it to a useable value by Linux.

	   All the IRQ values generated by the console are greater than 90,
	   so we subtract 80 because it is (90 - allocated ISA IRQ's).  */

	pci_read_config_byte(dev, PCI_INTERRUPT_LINE, &irq_orig);

	return irq_orig - 0x80;
}

static u8
eiger_swizzle(struct pci_dev *dev, u8 *pinp)
{
	struct pci_controller *hose = dev->sysdata;
	int slot, pin = *pinp;
	int bridge_count = 0;

	/* Find the number of backplane bridges.  */
	int backplane = inw(0x502) & 0x0f;

	switch (backplane)
	{
	   case 0x00: bridge_count = 0; break; /* No bridges */
	   case 0x01: bridge_count = 1; break; /* 1 */
	   case 0x03: bridge_count = 2; break; /* 2 */
	   case 0x07: bridge_count = 3; break; /* 3 */
	   case 0x0f: bridge_count = 4; break; /* 4 */
	};

	slot = PCI_SLOT(dev->devfn);
	while (dev->bus->self) {
		/* Check for built-in bridges on hose 0. */
		if (hose->index == 0
		    && (PCI_SLOT(dev->bus->self->devfn)
			> 20 - bridge_count)) {
			slot = PCI_SLOT(dev->devfn);
			break;
		}
		/* Must be a card-based bridge.  */
		pin = pci_swizzle_interrupt_pin(dev, pin);

		/* Move up the chain of bridges.  */
		dev = dev->bus->self;
	}
	*pinp = pin;
	return slot;
}

/*
 * The System Vectors
 */

struct alpha_machine_vector eiger_mv __initmv = {
	.vector_name		= "Eiger",
	DO_EV6_MMU,
	DO_DEFAULT_RTC,
	DO_TSUNAMI_IO,
	.machine_check		= tsunami_machine_check,
	.max_isa_dma_address	= ALPHA_MAX_ISA_DMA_ADDRESS,
	.min_io_address		= DEFAULT_IO_BASE,
	.min_mem_address	= DEFAULT_MEM_BASE,
	.pci_dac_offset		= TSUNAMI_DAC_OFFSET,

	.nr_irqs		= 128,
	.device_interrupt	= eiger_device_interrupt,

	.init_arch		= tsunami_init_arch,
	.init_irq		= eiger_init_irq,
	.init_rtc		= common_init_rtc,
	.init_pci		= common_init_pci,
	.kill_arch		= tsunami_kill_arch,
	.pci_map_irq		= eiger_map_irq,
	.pci_swizzle		= eiger_swizzle,
};
ALIAS_MV(eiger)
