/*
 * arch/parisc/kernel/firmware.c  - safe PDC access routines
 *
 *	PDC == Processor Dependent Code
 *
 * See http://www.parisc-linux.org/documentation/index.html
 * for documentation describing the entry points and calling
 * conventions defined below.
 *
 * Copyright 1999 SuSE GmbH Nuernberg (Philipp Rumpf, prumpf@tux.org)
 * Copyright 1999 The Puffin Group, (Alex deVries, David Kennedy)
 * Copyright 2003 Grant Grundler <grundler parisc-linux org>
 * Copyright 2003,2004 Ryan Bradetich <rbrad@parisc-linux.org>
 * Copyright 2004 Thibaut VARENE <varenet@parisc-linux.org>
 *
 *    This program is free software; you can redistribute it and/or modify
 *    it under the terms of the GNU General Public License as published by
 *    the Free Software Foundation; either version 2 of the License, or
 *    (at your option) any later version.
 *
 */

/*	I think it would be in everyone's best interest to follow this
 *	guidelines when writing PDC wrappers:
 *
 *	 - the name of the pdc wrapper should match one of the macros
 *	   used for the first two arguments
 *	 - don't use caps for random parts of the name
 *	 - use the static PDC result buffers and "copyout" to structs
 *	   supplied by the caller to encapsulate alignment restrictions
 *	 - hold pdc_lock while in PDC or using static result buffers
 *	 - use __pa() to convert virtual (kernel) pointers to physical
 *	   ones.
 *	 - the name of the struct used for pdc return values should equal
 *	   one of the macros used for the first two arguments to the
 *	   corresponding PDC call
 *	 - keep the order of arguments
 *	 - don't be smart (setting trailing NUL bytes for strings, return
 *	   something useful even if the call failed) unless you are sure
 *	   it's not going to affect functionality or performance
 *
 *	Example:
 *	int pdc_cache_info(struct pdc_cache_info *cache_info )
 *	{
 *		int retval;
 *
 *		spin_lock_irq(&pdc_lock);
 *		retval = mem_pdc_call(PDC_CACHE,PDC_CACHE_INFO,__pa(cache_info),0);
 *		convert_to_wide(pdc_result);
 *		memcpy(cache_info, pdc_result, sizeof(*cache_info));
 *		spin_unlock_irq(&pdc_lock);
 *
 *		return retval;
 *	}
 *					prumpf	991016	
 */

#include <stdarg.h>

#include <linux/delay.h>
#include <linux/init.h>
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/string.h>
#include <linux/spinlock.h>

#include <asm/page.h>
#include <asm/pdc.h>
#include <asm/pdcpat.h>
#include <asm/system.h>
#include <asm/processor.h>	/* for boot_cpu_data */

static DEFINE_SPINLOCK(pdc_lock);
static unsigned long pdc_result[32] __attribute__ ((aligned (8)));
static unsigned long pdc_result2[32] __attribute__ ((aligned (8)));

#ifdef __LP64__
#define WIDE_FIRMWARE 0x1
#define NARROW_FIRMWARE 0x2

/* Firmware needs to be initially set to narrow to determine the 
 * actual firmware width. */
int parisc_narrow_firmware __read_mostly = 1;
#endif

/* On most currently-supported platforms, IODC I/O calls are 32-bit calls
 * and MEM_PDC calls are always the same width as the OS.
 * Some PAT boxes may have 64-bit IODC I/O.
 *
 * Ryan Bradetich added the now obsolete CONFIG_PDC_NARROW to allow
 * 64-bit kernels to run on systems with 32-bit MEM_PDC calls.
 * This allowed wide kernels to run on Cxxx boxes.
 * We now detect 32-bit-only PDC and dynamically switch to 32-bit mode
 * when running a 64-bit kernel on such boxes (e.g. C200 or C360).
 */

#ifdef __LP64__
long real64_call(unsigned long function, ...);
#endif
long real32_call(unsigned long function, ...);

#ifdef __LP64__
#   define MEM_PDC (unsigned long)(PAGE0->mem_pdc_hi) << 32 | PAGE0->mem_pdc
#   define mem_pdc_call(args...) unlikely(parisc_narrow_firmware) ? real32_call(MEM_PDC, args) : real64_call(MEM_PDC, args)
#else
#   define MEM_PDC (unsigned long)PAGE0->mem_pdc
#   define mem_pdc_call(args...) real32_call(MEM_PDC, args)
#endif


/**
 * f_extend - Convert PDC addresses to kernel addresses.
 * @address: Address returned from PDC.
 *
 * This function is used to convert PDC addresses into kernel addresses
 * when the PDC address size and kernel address size are different.
 */
static unsigned long f_extend(unsigned long address)
{
#ifdef __LP64__
	if(unlikely(parisc_narrow_firmware)) {
		if((address & 0xff000000) == 0xf0000000)
			return 0xf0f0f0f000000000UL | (u32)address;

		if((address & 0xf0000000) == 0xf0000000)
			return 0xffffffff00000000UL | (u32)address;
	}
#endif
	return address;
}

/**
 * convert_to_wide - Convert the return buffer addresses into kernel addresses.
 * @address: The return buffer from PDC.
 *
 * This function is used to convert the return buffer addresses retrieved from PDC
 * into kernel addresses when the PDC address size and kernel address size are
 * different.
 */
static void convert_to_wide(unsigned long *addr)
{
#ifdef __LP64__
	int i;
	unsigned int *p = (unsigned int *)addr;

	if(unlikely(parisc_narrow_firmware)) {
		for(i = 31; i >= 0; --i)
			addr[i] = p[i];
	}
#endif
}

/**
 * set_firmware_width - Determine if the firmware is wide or narrow.
 * 
 * This function must be called before any pdc_* function that uses the convert_to_wide
 * function.
 */
void __init set_firmware_width(void)
{
#ifdef __LP64__
	int retval;

        spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_MODEL, PDC_MODEL_CAPABILITIES, __pa(pdc_result), 0);
	convert_to_wide(pdc_result);
	if(pdc_result[0] != NARROW_FIRMWARE)
		parisc_narrow_firmware = 0;
        spin_unlock_irq(&pdc_lock);
#endif
}

/**
 * pdc_emergency_unlock - Unlock the linux pdc lock
 *
 * This call unlocks the linux pdc lock in case we need some PDC functions
 * (like pdc_add_valid) during kernel stack dump.
 */
void pdc_emergency_unlock(void)
{
 	/* Spinlock DEBUG code freaks out if we unconditionally unlock */
        if (spin_is_locked(&pdc_lock))
		spin_unlock(&pdc_lock);
}


/**
 * pdc_add_valid - Verify address can be accessed without causing a HPMC.
 * @address: Address to be verified.
 *
 * This PDC call attempts to read from the specified address and verifies
 * if the address is valid.
 * 
 * The return value is PDC_OK (0) in case accessing this address is valid.
 */
int pdc_add_valid(unsigned long address)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_ADD_VALID, PDC_ADD_VALID_VERIFY, address);
        spin_unlock_irq(&pdc_lock);

        return retval;
}
EXPORT_SYMBOL(pdc_add_valid);

/**
 * pdc_chassis_info - Return chassis information.
 * @result: The return buffer.
 * @chassis_info: The memory buffer address.
 * @len: The size of the memory buffer address.
 *
 * An HVERSION dependent call for returning the chassis information.
 */
int __init pdc_chassis_info(struct pdc_chassis_info *chassis_info, void *led_info, unsigned long len)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        memcpy(&pdc_result, chassis_info, sizeof(*chassis_info));
        memcpy(&pdc_result2, led_info, len);
        retval = mem_pdc_call(PDC_CHASSIS, PDC_RETURN_CHASSIS_INFO,
                              __pa(pdc_result), __pa(pdc_result2), len);
        memcpy(chassis_info, pdc_result, sizeof(*chassis_info));
        memcpy(led_info, pdc_result2, len);
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/**
 * pdc_pat_chassis_send_log - Sends a PDC PAT CHASSIS log message.
 * @retval: -1 on error, 0 on success. Other value are PDC errors
 * 
 * Must be correctly formatted or expect system crash
 */
#ifdef __LP64__
int pdc_pat_chassis_send_log(unsigned long state, unsigned long data)
{
	int retval = 0;
        
	if (!is_pdc_pat())
		return -1;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_CHASSIS_LOG, PDC_PAT_CHASSIS_WRITE_LOG, __pa(&state), __pa(&data));
	spin_unlock_irq(&pdc_lock);

	return retval;
}
#endif

/**
 * pdc_chassis_disp - Updates display
 * @retval: -1 on error, 0 on success
 *
 * Works on old PDC only (E class, others?)
 */
int pdc_chassis_disp(unsigned long disp)
{
	int retval = 0;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_CHASSIS, PDC_CHASSIS_DISP, disp);
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_coproc_cfg - To identify coprocessors attached to the processor.
 * @pdc_coproc_info: Return buffer address.
 *
 * This PDC call returns the presence and status of all the coprocessors
 * attached to the processor.
 */
int __init pdc_coproc_cfg(struct pdc_coproc_cfg *pdc_coproc_info)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_COPROC, PDC_COPROC_CFG, __pa(pdc_result));
        convert_to_wide(pdc_result);
        pdc_coproc_info->ccr_functional = pdc_result[0];
        pdc_coproc_info->ccr_present = pdc_result[1];
        pdc_coproc_info->revision = pdc_result[17];
        pdc_coproc_info->model = pdc_result[18];
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/**
 * pdc_iodc_read - Read data from the modules IODC.
 * @actcnt: The actual number of bytes.
 * @hpa: The HPA of the module for the iodc read.
 * @index: The iodc entry point.
 * @iodc_data: A buffer memory for the iodc options.
 * @iodc_data_size: Size of the memory buffer.
 *
 * This PDC call reads from the IODC of the module specified by the hpa
 * argument.
 */
int pdc_iodc_read(unsigned long *actcnt, unsigned long hpa, unsigned int index,
		  void *iodc_data, unsigned int iodc_data_size)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_IODC, PDC_IODC_READ, __pa(pdc_result), hpa, 
			      index, __pa(pdc_result2), iodc_data_size);
	convert_to_wide(pdc_result);
	*actcnt = pdc_result[0];
	memcpy(iodc_data, pdc_result2, iodc_data_size);
	spin_unlock_irq(&pdc_lock);

	return retval;
}
EXPORT_SYMBOL(pdc_iodc_read);

/**
 * pdc_system_map_find_mods - Locate unarchitected modules.
 * @pdc_mod_info: Return buffer address.
 * @mod_path: pointer to dev path structure.
 * @mod_index: fixed address module index.
 *
 * To locate and identify modules which reside at fixed I/O addresses, which
 * do not self-identify via architected bus walks.
 */
int pdc_system_map_find_mods(struct pdc_system_map_mod_info *pdc_mod_info,
			     struct pdc_module_path *mod_path, long mod_index)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_SYSTEM_MAP, PDC_FIND_MODULE, __pa(pdc_result), 
			      __pa(pdc_result2), mod_index);
	convert_to_wide(pdc_result);
	memcpy(pdc_mod_info, pdc_result, sizeof(*pdc_mod_info));
	memcpy(mod_path, pdc_result2, sizeof(*mod_path));
	spin_unlock_irq(&pdc_lock);

	pdc_mod_info->mod_addr = f_extend(pdc_mod_info->mod_addr);
	return retval;
}

/**
 * pdc_system_map_find_addrs - Retrieve additional address ranges.
 * @pdc_addr_info: Return buffer address.
 * @mod_index: Fixed address module index.
 * @addr_index: Address range index.
 * 
 * Retrieve additional information about subsequent address ranges for modules
 * with multiple address ranges.  
 */
int pdc_system_map_find_addrs(struct pdc_system_map_addr_info *pdc_addr_info, 
			      long mod_index, long addr_index)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_SYSTEM_MAP, PDC_FIND_ADDRESS, __pa(pdc_result),
			      mod_index, addr_index);
	convert_to_wide(pdc_result);
	memcpy(pdc_addr_info, pdc_result, sizeof(*pdc_addr_info));
	spin_unlock_irq(&pdc_lock);

	pdc_addr_info->mod_addr = f_extend(pdc_addr_info->mod_addr);
	return retval;
}

/**
 * pdc_model_info - Return model information about the processor.
 * @model: The return buffer.
 *
 * Returns the version numbers, identifiers, and capabilities from the processor module.
 */
int pdc_model_info(struct pdc_model *model) 
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_MODEL, PDC_MODEL_INFO, __pa(pdc_result), 0);
	convert_to_wide(pdc_result);
	memcpy(model, pdc_result, sizeof(*model));
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_model_sysmodel - Get the system model name.
 * @name: A char array of at least 81 characters.
 *
 * Get system model name from PDC ROM (e.g. 9000/715 or 9000/778/B160L)
 */
int pdc_model_sysmodel(char *name)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_MODEL, PDC_MODEL_SYSMODEL, __pa(pdc_result),
                              OS_ID_HPUX, __pa(name));
        convert_to_wide(pdc_result);

        if (retval == PDC_OK) {
                name[pdc_result[0]] = '\0'; /* add trailing '\0' */
        } else {
                name[0] = 0;
        }
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/**
 * pdc_model_versions - Identify the version number of each processor.
 * @cpu_id: The return buffer.
 * @id: The id of the processor to check.
 *
 * Returns the version number for each processor component.
 *
 * This comment was here before, but I do not know what it means :( -RB
 * id: 0 = cpu revision, 1 = boot-rom-version
 */
int pdc_model_versions(unsigned long *versions, int id)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_MODEL, PDC_MODEL_VERSIONS, __pa(pdc_result), id);
        convert_to_wide(pdc_result);
        *versions = pdc_result[0];
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/**
 * pdc_model_cpuid - Returns the CPU_ID.
 * @cpu_id: The return buffer.
 *
 * Returns the CPU_ID value which uniquely identifies the cpu portion of
 * the processor module.
 */
int pdc_model_cpuid(unsigned long *cpu_id)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        pdc_result[0] = 0; /* preset zero (call may not be implemented!) */
        retval = mem_pdc_call(PDC_MODEL, PDC_MODEL_CPU_ID, __pa(pdc_result), 0);
        convert_to_wide(pdc_result);
        *cpu_id = pdc_result[0];
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/**
 * pdc_model_capabilities - Returns the platform capabilities.
 * @capabilities: The return buffer.
 *
 * Returns information about platform support for 32- and/or 64-bit
 * OSes, IO-PDIR coherency, and virtual aliasing.
 */
int pdc_model_capabilities(unsigned long *capabilities)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        pdc_result[0] = 0; /* preset zero (call may not be implemented!) */
        retval = mem_pdc_call(PDC_MODEL, PDC_MODEL_CAPABILITIES, __pa(pdc_result), 0);
        convert_to_wide(pdc_result);
        *capabilities = pdc_result[0];
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/**
 * pdc_cache_info - Return cache and TLB information.
 * @cache_info: The return buffer.
 *
 * Returns information about the processor's cache and TLB.
 */
int pdc_cache_info(struct pdc_cache_info *cache_info)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_CACHE, PDC_CACHE_INFO, __pa(pdc_result), 0);
        convert_to_wide(pdc_result);
        memcpy(cache_info, pdc_result, sizeof(*cache_info));
        spin_unlock_irq(&pdc_lock);

        return retval;
}

#ifndef CONFIG_PA20
/**
 * pdc_btlb_info - Return block TLB information.
 * @btlb: The return buffer.
 *
 * Returns information about the hardware Block TLB.
 */
int pdc_btlb_info(struct pdc_btlb_info *btlb) 
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_BLOCK_TLB, PDC_BTLB_INFO, __pa(pdc_result), 0);
        memcpy(btlb, pdc_result, sizeof(*btlb));
        spin_unlock_irq(&pdc_lock);

        if(retval < 0) {
                btlb->max_size = 0;
        }
        return retval;
}

/**
 * pdc_mem_map_hpa - Find fixed module information.  
 * @address: The return buffer
 * @mod_path: pointer to dev path structure.
 *
 * This call was developed for S700 workstations to allow the kernel to find
 * the I/O devices (Core I/O). In the future (Kittyhawk and beyond) this
 * call will be replaced (on workstations) by the architected PDC_SYSTEM_MAP
 * call.
 *
 * This call is supported by all existing S700 workstations (up to  Gecko).
 */
int pdc_mem_map_hpa(struct pdc_memory_map *address,
		struct pdc_module_path *mod_path)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        memcpy(pdc_result2, mod_path, sizeof(*mod_path));
        retval = mem_pdc_call(PDC_MEM_MAP, PDC_MEM_MAP_HPA, __pa(pdc_result),
				__pa(pdc_result2));
        memcpy(address, pdc_result, sizeof(*address));
        spin_unlock_irq(&pdc_lock);

        return retval;
}
#endif	/* !CONFIG_PA20 */

/**
 * pdc_lan_station_id - Get the LAN address.
 * @lan_addr: The return buffer.
 * @hpa: The network device HPA.
 *
 * Get the LAN station address when it is not directly available from the LAN hardware.
 */
int pdc_lan_station_id(char *lan_addr, unsigned long hpa)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_LAN_STATION_ID, PDC_LAN_STATION_ID_READ,
			__pa(pdc_result), hpa);
	if (retval < 0) {
		/* FIXME: else read MAC from NVRAM */
		memset(lan_addr, 0, PDC_LAN_STATION_ID_SIZE);
	} else {
		memcpy(lan_addr, pdc_result, PDC_LAN_STATION_ID_SIZE);
	}
	spin_unlock_irq(&pdc_lock);

	return retval;
}
EXPORT_SYMBOL(pdc_lan_station_id);

/**
 * pdc_stable_read - Read data from Stable Storage.
 * @staddr: Stable Storage address to access.
 * @memaddr: The memory address where Stable Storage data shall be copied.
 * @count: number of bytes to transfert. count is multiple of 4.
 *
 * This PDC call reads from the Stable Storage address supplied in staddr
 * and copies count bytes to the memory address memaddr.
 * The call will fail if staddr+count > PDC_STABLE size.
 */
int pdc_stable_read(unsigned long staddr, void *memaddr, unsigned long count)
{
       int retval;

       spin_lock_irq(&pdc_lock);
       retval = mem_pdc_call(PDC_STABLE, PDC_STABLE_READ, staddr,
               __pa(pdc_result), count);
       convert_to_wide(pdc_result);
       memcpy(memaddr, pdc_result, count);
       spin_unlock_irq(&pdc_lock);

       return retval;
}
EXPORT_SYMBOL(pdc_stable_read);

/**
 * pdc_stable_write - Write data to Stable Storage.
 * @staddr: Stable Storage address to access.
 * @memaddr: The memory address where Stable Storage data shall be read from.
 * @count: number of bytes to transfert. count is multiple of 4.
 *
 * This PDC call reads count bytes from the supplied memaddr address,
 * and copies count bytes to the Stable Storage address staddr.
 * The call will fail if staddr+count > PDC_STABLE size.
 */
int pdc_stable_write(unsigned long staddr, void *memaddr, unsigned long count)
{
       int retval;

       spin_lock_irq(&pdc_lock);
       memcpy(pdc_result, memaddr, count);
       convert_to_wide(pdc_result);
       retval = mem_pdc_call(PDC_STABLE, PDC_STABLE_WRITE, staddr,
               __pa(pdc_result), count);
       spin_unlock_irq(&pdc_lock);

       return retval;
}
EXPORT_SYMBOL(pdc_stable_write);

/**
 * pdc_stable_get_size - Get Stable Storage size in bytes.
 * @size: pointer where the size will be stored.
 *
 * This PDC call returns the number of bytes in the processor's Stable
 * Storage, which is the number of contiguous bytes implemented in Stable
 * Storage starting from staddr=0. size in an unsigned 64-bit integer
 * which is a multiple of four.
 */
int pdc_stable_get_size(unsigned long *size)
{
       int retval;

       spin_lock_irq(&pdc_lock);
       retval = mem_pdc_call(PDC_STABLE, PDC_STABLE_RETURN_SIZE, __pa(pdc_result));
       *size = pdc_result[0];
       spin_unlock_irq(&pdc_lock);

       return retval;
}
EXPORT_SYMBOL(pdc_stable_get_size);

/**
 * pdc_stable_verify_contents - Checks that Stable Storage contents are valid.
 *
 * This PDC call is meant to be used to check the integrity of the current
 * contents of Stable Storage.
 */
int pdc_stable_verify_contents(void)
{
       int retval;

       spin_lock_irq(&pdc_lock);
       retval = mem_pdc_call(PDC_STABLE, PDC_STABLE_VERIFY_CONTENTS);
       spin_unlock_irq(&pdc_lock);

       return retval;
}
EXPORT_SYMBOL(pdc_stable_verify_contents);

/**
 * pdc_stable_initialize - Sets Stable Storage contents to zero and initialize
 * the validity indicator.
 *
 * This PDC call will erase all contents of Stable Storage. Use with care!
 */
int pdc_stable_initialize(void)
{
       int retval;

       spin_lock_irq(&pdc_lock);
       retval = mem_pdc_call(PDC_STABLE, PDC_STABLE_INITIALIZE);
       spin_unlock_irq(&pdc_lock);

       return retval;
}
EXPORT_SYMBOL(pdc_stable_initialize);

/**
 * pdc_get_initiator - Get the SCSI Interface Card params (SCSI ID, SDTR, SE or LVD)
 * @hwpath: fully bc.mod style path to the device.
 * @initiator: the array to return the result into
 *
 * Get the SCSI operational parameters from PDC.
 * Needed since HPUX never used BIOS or symbios card NVRAM.
 * Most ncr/sym cards won't have an entry and just use whatever
 * capabilities of the card are (eg Ultra, LVD). But there are
 * several cases where it's useful:
 *    o set SCSI id for Multi-initiator clusters,
 *    o cable too long (ie SE scsi 10Mhz won't support 6m length),
 *    o bus width exported is less than what the interface chip supports.
 */
int pdc_get_initiator(struct hardware_path *hwpath, struct pdc_initiator *initiator)
{
	int retval;

	spin_lock_irq(&pdc_lock);

/* BCJ-XXXX series boxes. E.G. "9000/785/C3000" */
#define IS_SPROCKETS() (strlen(boot_cpu_data.pdc.sys_model_name) == 14 && \
	strncmp(boot_cpu_data.pdc.sys_model_name, "9000/785", 8) == 0)

	retval = mem_pdc_call(PDC_INITIATOR, PDC_GET_INITIATOR, 
			      __pa(pdc_result), __pa(hwpath));
	if (retval < PDC_OK)
		goto out;

	if (pdc_result[0] < 16) {
		initiator->host_id = pdc_result[0];
	} else {
		initiator->host_id = -1;
	}

	/*
	 * Sprockets and Piranha return 20 or 40 (MT/s).  Prelude returns
	 * 1, 2, 5 or 10 for 5, 10, 20 or 40 MT/s, respectively
	 */
	switch (pdc_result[1]) {
		case  1: initiator->factor = 50; break;
		case  2: initiator->factor = 25; break;
		case  5: initiator->factor = 12; break;
		case 25: initiator->factor = 10; break;
		case 20: initiator->factor = 12; break;
		case 40: initiator->factor = 10; break;
		default: initiator->factor = -1; break;
	}

	if (IS_SPROCKETS()) {
		initiator->width = pdc_result[4];
		initiator->mode = pdc_result[5];
	} else {
		initiator->width = -1;
		initiator->mode = -1;
	}

 out:
	spin_unlock_irq(&pdc_lock);
	return (retval >= PDC_OK);
}
EXPORT_SYMBOL(pdc_get_initiator);


/**
 * pdc_pci_irt_size - Get the number of entries in the interrupt routing table.
 * @num_entries: The return value.
 * @hpa: The HPA for the device.
 *
 * This PDC function returns the number of entries in the specified cell's
 * interrupt table.
 * Similar to PDC_PAT stuff - but added for Forte/Allegro boxes
 */ 
int pdc_pci_irt_size(unsigned long *num_entries, unsigned long hpa)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PCI_INDEX, PDC_PCI_GET_INT_TBL_SIZE, 
			      __pa(pdc_result), hpa);
	convert_to_wide(pdc_result);
	*num_entries = pdc_result[0];
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/** 
 * pdc_pci_irt - Get the PCI interrupt routing table.
 * @num_entries: The number of entries in the table.
 * @hpa: The Hard Physical Address of the device.
 * @tbl: 
 *
 * Get the PCI interrupt routing table for the device at the given HPA.
 * Similar to PDC_PAT stuff - but added for Forte/Allegro boxes
 */
int pdc_pci_irt(unsigned long num_entries, unsigned long hpa, void *tbl)
{
	int retval;

	BUG_ON((unsigned long)tbl & 0x7);

	spin_lock_irq(&pdc_lock);
	pdc_result[0] = num_entries;
	retval = mem_pdc_call(PDC_PCI_INDEX, PDC_PCI_GET_INT_TBL, 
			      __pa(pdc_result), hpa, __pa(tbl));
	spin_unlock_irq(&pdc_lock);

	return retval;
}


#if 0	/* UNTEST CODE - left here in case someone needs it */

/** 
 * pdc_pci_config_read - read PCI config space.
 * @hpa		token from PDC to indicate which PCI device
 * @pci_addr	configuration space address to read from
 *
 * Read PCI Configuration space *before* linux PCI subsystem is running.
 */
unsigned int pdc_pci_config_read(void *hpa, unsigned long cfg_addr)
{
	int retval;
	spin_lock_irq(&pdc_lock);
	pdc_result[0] = 0;
	pdc_result[1] = 0;
	retval = mem_pdc_call(PDC_PCI_INDEX, PDC_PCI_READ_CONFIG, 
			      __pa(pdc_result), hpa, cfg_addr&~3UL, 4UL);
	spin_unlock_irq(&pdc_lock);
	return retval ? ~0 : (unsigned int) pdc_result[0];
}


/** 
 * pdc_pci_config_write - read PCI config space.
 * @hpa		token from PDC to indicate which PCI device
 * @pci_addr	configuration space address to write
 * @val		value we want in the 32-bit register
 *
 * Write PCI Configuration space *before* linux PCI subsystem is running.
 */
void pdc_pci_config_write(void *hpa, unsigned long cfg_addr, unsigned int val)
{
	int retval;
	spin_lock_irq(&pdc_lock);
	pdc_result[0] = 0;
	retval = mem_pdc_call(PDC_PCI_INDEX, PDC_PCI_WRITE_CONFIG, 
			      __pa(pdc_result), hpa,
			      cfg_addr&~3UL, 4UL, (unsigned long) val);
	spin_unlock_irq(&pdc_lock);
	return retval;
}
#endif /* UNTESTED CODE */

/**
 * pdc_tod_read - Read the Time-Of-Day clock.
 * @tod: The return buffer:
 *
 * Read the Time-Of-Day clock
 */
int pdc_tod_read(struct pdc_tod *tod)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_TOD, PDC_TOD_READ, __pa(pdc_result), 0);
        convert_to_wide(pdc_result);
        memcpy(tod, pdc_result, sizeof(*tod));
        spin_unlock_irq(&pdc_lock);

        return retval;
}
EXPORT_SYMBOL(pdc_tod_read);

/**
 * pdc_tod_set - Set the Time-Of-Day clock.
 * @sec: The number of seconds since epoch.
 * @usec: The number of micro seconds.
 *
 * Set the Time-Of-Day clock.
 */ 
int pdc_tod_set(unsigned long sec, unsigned long usec)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_TOD, PDC_TOD_WRITE, sec, usec);
        spin_unlock_irq(&pdc_lock);

        return retval;
}
EXPORT_SYMBOL(pdc_tod_set);

#ifdef __LP64__
int pdc_mem_mem_table(struct pdc_memory_table_raddr *r_addr,
		struct pdc_memory_table *tbl, unsigned long entries)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_MEM, PDC_MEM_TABLE, __pa(pdc_result), __pa(pdc_result2), entries);
	convert_to_wide(pdc_result);
	memcpy(r_addr, pdc_result, sizeof(*r_addr));
	memcpy(tbl, pdc_result2, entries * sizeof(*tbl));
	spin_unlock_irq(&pdc_lock);

	return retval;
}
#endif /* __LP64__ */

/* FIXME: Is this pdc used?  I could not find type reference to ftc_bitmap
 * so I guessed at unsigned long.  Someone who knows what this does, can fix
 * it later. :)
 */
int pdc_do_firm_test_reset(unsigned long ftc_bitmap)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_BROADCAST_RESET, PDC_DO_FIRM_TEST_RESET,
                              PDC_FIRM_TEST_MAGIC, ftc_bitmap);
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/*
 * pdc_do_reset - Reset the system.
 *
 * Reset the system.
 */
int pdc_do_reset(void)
{
        int retval;

        spin_lock_irq(&pdc_lock);
        retval = mem_pdc_call(PDC_BROADCAST_RESET, PDC_DO_RESET);
        spin_unlock_irq(&pdc_lock);

        return retval;
}

/*
 * pdc_soft_power_info - Enable soft power switch.
 * @power_reg: address of soft power register
 *
 * Return the absolute address of the soft power switch register
 */
int __init pdc_soft_power_info(unsigned long *power_reg)
{
	int retval;

	*power_reg = (unsigned long) (-1);
	
	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_SOFT_POWER, PDC_SOFT_POWER_INFO, __pa(pdc_result), 0);
	if (retval == PDC_OK) {
                convert_to_wide(pdc_result);
                *power_reg = f_extend(pdc_result[0]);
	}
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/*
 * pdc_soft_power_button - Control the soft power button behaviour
 * @sw_control: 0 for hardware control, 1 for software control 
 *
 *
 * This PDC function places the soft power button under software or
 * hardware control.
 * Under software control the OS may control to when to allow to shut 
 * down the system. Under hardware control pressing the power button 
 * powers off the system immediately.
 */
int pdc_soft_power_button(int sw_control)
{
	int retval;
	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_SOFT_POWER, PDC_SOFT_POWER_ENABLE, __pa(pdc_result), sw_control);
	spin_unlock_irq(&pdc_lock);
	return retval;
}

/*
 * pdc_io_reset - Hack to avoid overlapping range registers of Bridges devices.
 * Primarily a problem on T600 (which parisc-linux doesn't support) but
 * who knows what other platform firmware might do with this OS "hook".
 */
void pdc_io_reset(void)
{
	spin_lock_irq(&pdc_lock);  
	mem_pdc_call(PDC_IO, PDC_IO_RESET, 0);
	spin_unlock_irq(&pdc_lock);
}

/*
 * pdc_io_reset_devices - Hack to Stop USB controller
 *
 * If PDC used the usb controller, the usb controller
 * is still running and will crash the machines during iommu 
 * setup, because of still running DMA. This PDC call
 * stops the USB controller.
 * Normally called after calling pdc_io_reset().
 */
void pdc_io_reset_devices(void)
{
	spin_lock_irq(&pdc_lock);  
	mem_pdc_call(PDC_IO, PDC_IO_RESET_DEVICES, 0);
	spin_unlock_irq(&pdc_lock);
}


/**
 * pdc_iodc_putc - Console character print using IODC.
 * @c: the character to output.
 *
 * Note that only these special chars are architected for console IODC io:
 * BEL, BS, CR, and LF. Others are passed through.
 * Since the HP console requires CR+LF to perform a 'newline', we translate
 * "\n" to "\r\n".
 */
void pdc_iodc_putc(unsigned char c)
{
        /* XXX Should we spinlock posx usage */
        static int posx;        /* for simple TAB-Simulation... */
        static int __attribute__((aligned(8)))   iodc_retbuf[32];
        static char __attribute__((aligned(64))) iodc_dbuf[4096];
        unsigned int n;
	unsigned int flags;

        switch (c) {
        case '\n':
                iodc_dbuf[0] = '\r';
                iodc_dbuf[1] = '\n';
                n = 2;
                posx = 0;
                break;
        case '\t':
                pdc_iodc_putc(' ');
                while (posx & 7)        /* expand TAB */
                        pdc_iodc_putc(' ');
                return;         /* return since IODC can't handle this */
        case '\b':
                posx-=2;                /* BS */
        default:
                iodc_dbuf[0] = c;
                n = 1;
                posx++;
                break;
        }

        spin_lock_irqsave(&pdc_lock, flags);
        real32_call(PAGE0->mem_cons.iodc_io,
                    (unsigned long)PAGE0->mem_cons.hpa, ENTRY_IO_COUT,
                    PAGE0->mem_cons.spa, __pa(PAGE0->mem_cons.dp.layers),
                    __pa(iodc_retbuf), 0, __pa(iodc_dbuf), n, 0);
        spin_unlock_irqrestore(&pdc_lock, flags);
}

/**
 * pdc_iodc_outc - Console character print using IODC (without conversions).
 * @c: the character to output.
 *
 * Write the character directly to the IODC console.
 */
void pdc_iodc_outc(unsigned char c)
{
	unsigned int n, flags;

	/* fill buffer with one caracter and print it */
        static int __attribute__((aligned(8)))   iodc_retbuf[32];
        static char __attribute__((aligned(64))) iodc_dbuf[4096];

	n = 1;
	iodc_dbuf[0] = c;

	spin_lock_irqsave(&pdc_lock, flags);
	real32_call(PAGE0->mem_cons.iodc_io,
		    (unsigned long)PAGE0->mem_cons.hpa, ENTRY_IO_COUT,
		    PAGE0->mem_cons.spa, __pa(PAGE0->mem_cons.dp.layers),
		    __pa(iodc_retbuf), 0, __pa(iodc_dbuf), n, 0);
	spin_unlock_irqrestore(&pdc_lock, flags);
}

/**
 * pdc_iodc_getc - Read a character (non-blocking) from the PDC console.
 *
 * Read a character (non-blocking) from the PDC console, returns -1 if
 * key is not present.
 */
int pdc_iodc_getc(void)
{
	unsigned int flags;
        static int __attribute__((aligned(8)))   iodc_retbuf[32];
        static char __attribute__((aligned(64))) iodc_dbuf[4096];
	int ch;
	int status;

	/* Bail if no console input device. */
	if (!PAGE0->mem_kbd.iodc_io)
		return 0;
	
	/* wait for a keyboard (rs232)-input */
	spin_lock_irqsave(&pdc_lock, flags);
	real32_call(PAGE0->mem_kbd.iodc_io,
		    (unsigned long)PAGE0->mem_kbd.hpa, ENTRY_IO_CIN,
		    PAGE0->mem_kbd.spa, __pa(PAGE0->mem_kbd.dp.layers), 
		    __pa(iodc_retbuf), 0, __pa(iodc_dbuf), 1, 0);

	ch = *iodc_dbuf;
	status = *iodc_retbuf;
	spin_unlock_irqrestore(&pdc_lock, flags);

	if (status == 0)
	    return -1;
	
	return ch;
}

int pdc_sti_call(unsigned long func, unsigned long flags,
                 unsigned long inptr, unsigned long outputr,
                 unsigned long glob_cfg)
{
        int retval;

        spin_lock_irq(&pdc_lock);  
        retval = real32_call(func, flags, inptr, outputr, glob_cfg);
        spin_unlock_irq(&pdc_lock);

        return retval;
}
EXPORT_SYMBOL(pdc_sti_call);

#ifdef __LP64__
/**
 * pdc_pat_cell_get_number - Returns the cell number.
 * @cell_info: The return buffer.
 *
 * This PDC call returns the cell number of the cell from which the call
 * is made.
 */
int pdc_pat_cell_get_number(struct pdc_pat_cell_num *cell_info)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_CELL, PDC_PAT_CELL_GET_NUMBER, __pa(pdc_result));
	memcpy(cell_info, pdc_result, sizeof(*cell_info));
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_cell_module - Retrieve the cell's module information.
 * @actcnt: The number of bytes written to mem_addr.
 * @ploc: The physical location.
 * @mod: The module index.
 * @view_type: The view of the address type.
 * @mem_addr: The return buffer.
 *
 * This PDC call returns information about each module attached to the cell
 * at the specified location.
 */
int pdc_pat_cell_module(unsigned long *actcnt, unsigned long ploc, unsigned long mod,
			unsigned long view_type, void *mem_addr)
{
	int retval;
	static struct pdc_pat_cell_mod_maddr_block result __attribute__ ((aligned (8)));

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_CELL, PDC_PAT_CELL_MODULE, __pa(pdc_result), 
			      ploc, mod, view_type, __pa(&result));
	if(!retval) {
		*actcnt = pdc_result[0];
		memcpy(mem_addr, &result, *actcnt);
	}
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_cpu_get_number - Retrieve the cpu number.
 * @cpu_info: The return buffer.
 * @hpa: The Hard Physical Address of the CPU.
 *
 * Retrieve the cpu number for the cpu at the specified HPA.
 */
int pdc_pat_cpu_get_number(struct pdc_pat_cpu_num *cpu_info, void *hpa)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_CPU, PDC_PAT_CPU_GET_NUMBER,
			      __pa(&pdc_result), hpa);
	memcpy(cpu_info, pdc_result, sizeof(*cpu_info));
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_get_irt_size - Retrieve the number of entries in the cell's interrupt table.
 * @num_entries: The return value.
 * @cell_num: The target cell.
 *
 * This PDC function returns the number of entries in the specified cell's
 * interrupt table.
 */
int pdc_pat_get_irt_size(unsigned long *num_entries, unsigned long cell_num)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_IO, PDC_PAT_IO_GET_PCI_ROUTING_TABLE_SIZE,
			      __pa(pdc_result), cell_num);
	*num_entries = pdc_result[0];
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_get_irt - Retrieve the cell's interrupt table.
 * @r_addr: The return buffer.
 * @cell_num: The target cell.
 *
 * This PDC function returns the actual interrupt table for the specified cell.
 */
int pdc_pat_get_irt(void *r_addr, unsigned long cell_num)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_IO, PDC_PAT_IO_GET_PCI_ROUTING_TABLE,
			      __pa(r_addr), cell_num);
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_pd_get_addr_map - Retrieve information about memory address ranges.
 * @actlen: The return buffer.
 * @mem_addr: Pointer to the memory buffer.
 * @count: The number of bytes to read from the buffer.
 * @offset: The offset with respect to the beginning of the buffer.
 *
 */
int pdc_pat_pd_get_addr_map(unsigned long *actual_len, void *mem_addr, 
			    unsigned long count, unsigned long offset)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_PD, PDC_PAT_PD_GET_ADDR_MAP, __pa(pdc_result), 
			      __pa(pdc_result2), count, offset);
	*actual_len = pdc_result[0];
	memcpy(mem_addr, pdc_result2, *actual_len);
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_io_pci_cfg_read - Read PCI configuration space.
 * @pci_addr: PCI configuration space address for which the read request is being made.
 * @pci_size: Size of read in bytes. Valid values are 1, 2, and 4. 
 * @mem_addr: Pointer to return memory buffer.
 *
 */
int pdc_pat_io_pci_cfg_read(unsigned long pci_addr, int pci_size, u32 *mem_addr)
{
	int retval;
	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_IO, PDC_PAT_IO_PCI_CONFIG_READ,
					__pa(pdc_result), pci_addr, pci_size);
	switch(pci_size) {
		case 1: *(u8 *) mem_addr =  (u8)  pdc_result[0];
		case 2: *(u16 *)mem_addr =  (u16) pdc_result[0];
		case 4: *(u32 *)mem_addr =  (u32) pdc_result[0];
	}
	spin_unlock_irq(&pdc_lock);

	return retval;
}

/**
 * pdc_pat_io_pci_cfg_write - Retrieve information about memory address ranges.
 * @pci_addr: PCI configuration space address for which the write  request is being made.
 * @pci_size: Size of write in bytes. Valid values are 1, 2, and 4. 
 * @value: Pointer to 1, 2, or 4 byte value in low order end of argument to be 
 *         written to PCI Config space.
 *
 */
int pdc_pat_io_pci_cfg_write(unsigned long pci_addr, int pci_size, u32 val)
{
	int retval;

	spin_lock_irq(&pdc_lock);
	retval = mem_pdc_call(PDC_PAT_IO, PDC_PAT_IO_PCI_CONFIG_WRITE,
				pci_addr, pci_size, val);
	spin_unlock_irq(&pdc_lock);

	return retval;
}
#endif /* __LP64__ */


/***************** 32-bit real-mode calls ***********/
/* The struct below is used
 * to overlay real_stack (real2.S), preparing a 32-bit call frame.
 * real32_call_asm() then uses this stack in narrow real mode
 */

struct narrow_stack {
	/* use int, not long which is 64 bits */
	unsigned int arg13;
	unsigned int arg12;
	unsigned int arg11;
	unsigned int arg10;
	unsigned int arg9;
	unsigned int arg8;
	unsigned int arg7;
	unsigned int arg6;
	unsigned int arg5;
	unsigned int arg4;
	unsigned int arg3;
	unsigned int arg2;
	unsigned int arg1;
	unsigned int arg0;
	unsigned int frame_marker[8];
	unsigned int sp;
	/* in reality, there's nearly 8k of stack after this */
};

long real32_call(unsigned long fn, ...)
{
	va_list args;
	extern struct narrow_stack real_stack;
	extern unsigned long real32_call_asm(unsigned int *,
					     unsigned int *, 
					     unsigned int);
	
	va_start(args, fn);
	real_stack.arg0 = va_arg(args, unsigned int);
	real_stack.arg1 = va_arg(args, unsigned int);
	real_stack.arg2 = va_arg(args, unsigned int);
	real_stack.arg3 = va_arg(args, unsigned int);
	real_stack.arg4 = va_arg(args, unsigned int);
	real_stack.arg5 = va_arg(args, unsigned int);
	real_stack.arg6 = va_arg(args, unsigned int);
	real_stack.arg7 = va_arg(args, unsigned int);
	real_stack.arg8 = va_arg(args, unsigned int);
	real_stack.arg9 = va_arg(args, unsigned int);
	real_stack.arg10 = va_arg(args, unsigned int);
	real_stack.arg11 = va_arg(args, unsigned int);
	real_stack.arg12 = va_arg(args, unsigned int);
	real_stack.arg13 = va_arg(args, unsigned int);
	va_end(args);
	
	return real32_call_asm(&real_stack.sp, &real_stack.arg0, fn);
}

#ifdef __LP64__
/***************** 64-bit real-mode calls ***********/

struct wide_stack {
	unsigned long arg0;
	unsigned long arg1;
	unsigned long arg2;
	unsigned long arg3;
	unsigned long arg4;
	unsigned long arg5;
	unsigned long arg6;
	unsigned long arg7;
	unsigned long arg8;
	unsigned long arg9;
	unsigned long arg10;
	unsigned long arg11;
	unsigned long arg12;
	unsigned long arg13;
	unsigned long frame_marker[2];	/* rp, previous sp */
	unsigned long sp;
	/* in reality, there's nearly 8k of stack after this */
};

long real64_call(unsigned long fn, ...)
{
	va_list args;
	extern struct wide_stack real64_stack;
	extern unsigned long real64_call_asm(unsigned long *,
					     unsigned long *, 
					     unsigned long);
    
	va_start(args, fn);
	real64_stack.arg0 = va_arg(args, unsigned long);
	real64_stack.arg1 = va_arg(args, unsigned long);
	real64_stack.arg2 = va_arg(args, unsigned long);
	real64_stack.arg3 = va_arg(args, unsigned long);
	real64_stack.arg4 = va_arg(args, unsigned long);
	real64_stack.arg5 = va_arg(args, unsigned long);
	real64_stack.arg6 = va_arg(args, unsigned long);
	real64_stack.arg7 = va_arg(args, unsigned long);
	real64_stack.arg8 = va_arg(args, unsigned long);
	real64_stack.arg9 = va_arg(args, unsigned long);
	real64_stack.arg10 = va_arg(args, unsigned long);
	real64_stack.arg11 = va_arg(args, unsigned long);
	real64_stack.arg12 = va_arg(args, unsigned long);
	real64_stack.arg13 = va_arg(args, unsigned long);
	va_end(args);
	
	return real64_call_asm(&real64_stack.sp, &real64_stack.arg0, fn);
}

#endif /* __LP64__ */

