/* 
 * IUCV network driver
 *
 * Copyright (C) 2001 IBM Deutschland Entwicklung GmbH, IBM Corporation
 * Author(s):
 *    Original source:
 *      Alan Altmark (Alan_Altmark@us.ibm.com)  Sept. 2000
 *      Xenia Tkatschow (xenia@us.ibm.com)
 *    2Gb awareness and general cleanup:
 *      Fritz Elfert (elfert@de.ibm.com, felfert@millenux.com)
 *
 * Documentation used:
 *    The original source
 *    CP Programming Service, IBM document # SC24-5760
 *
 * 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, or (at your option)
 * any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 *
 */

/* #define DEBUG */

#include <linux/module.h>
#include <linux/moduleparam.h>
#include <linux/config.h>

#include <linux/spinlock.h>
#include <linux/kernel.h>
#include <linux/slab.h>
#include <linux/init.h>
#include <linux/interrupt.h>
#include <linux/list.h>
#include <linux/errno.h>
#include <linux/err.h>
#include <linux/device.h>
#include <asm/atomic.h>
#include "iucv.h"
#include <asm/io.h>
#include <asm/s390_ext.h>
#include <asm/ebcdic.h>
#include <asm/smp.h>
#include <asm/s390_rdev.h>

/* FLAGS:
 * All flags are defined in the field IPFLAGS1 of each function
 * and can be found in CP Programming Services.
 * IPSRCCLS - Indicates you have specified a source class
 * IPFGMCL  - Indicates you have specified a target class
 * IPFGPID  - Indicates you have specified a pathid
 * IPFGMID  - Indicates you have specified a message ID
 * IPANSLST - Indicates that you are using an address list for
 *            reply data
 * IPBUFLST - Indicates that you are using an address list for
 *            message data
 */

#define IPSRCCLS 	0x01
#define IPFGMCL         0x01
#define IPFGPID         0x02
#define IPFGMID         0x04
#define IPANSLST        0x08
#define IPBUFLST        0x40

static int
iucv_bus_match (struct device *dev, struct device_driver *drv)
{
	return 0;
}

struct bus_type iucv_bus = {
	.name = "iucv",
	.match = iucv_bus_match,
};	

struct device *iucv_root;

/* General IUCV interrupt structure */
typedef struct {
	__u16 ippathid;
	__u8  res1;
	__u8  iptype;
	__u32 res2;
	__u8  ipvmid[8];
	__u8  res3[24];
} iucv_GeneralInterrupt;

static iucv_GeneralInterrupt *iucv_external_int_buffer = NULL;

/* Spin Lock declaration */

static DEFINE_SPINLOCK(iucv_lock);

static int messagesDisabled = 0;

/***************INTERRUPT HANDLING ***************/

typedef struct {
	struct list_head queue;
	iucv_GeneralInterrupt data;
} iucv_irqdata;

static struct list_head  iucv_irq_queue;
static DEFINE_SPINLOCK(iucv_irq_queue_lock);

/*
 *Internal function prototypes
 */
static void iucv_tasklet_handler(unsigned long);
static void iucv_irq_handler(struct pt_regs *, __u16);

static DECLARE_TASKLET(iucv_tasklet,iucv_tasklet_handler,0);

/************ FUNCTION ID'S ****************************/

#define ACCEPT          10
#define CONNECT         11
#define DECLARE_BUFFER  12
#define PURGE           9
#define QUERY           0
#define QUIESCE         13
#define RECEIVE         5
#define REJECT          8
#define REPLY           6
#define RESUME          14
#define RETRIEVE_BUFFER 2
#define SEND            4
#define SETMASK         16
#define SEVER           15

/**
 * Structure: handler
 * members: list - list management.
 *          structure: id
 *             userid - 8 char array of machine identification
 *             user_data - 16 char array for user identification
 *             mask - 24 char array used to compare the 2 previous
 *          interrupt_table - vector of interrupt functions.
 *          pgm_data -  ulong, application data that is passed
 *                      to the interrupt handlers
*/
typedef struct handler_t {
	struct list_head list;
	struct {
		__u8 userid[8];
		__u8 user_data[16];
		__u8 mask[24];
	}                    id;
	iucv_interrupt_ops_t *interrupt_table;
	void                 *pgm_data;
} handler;

/**
 * iucv_handler_table: List of registered handlers.
 */
static struct list_head iucv_handler_table;

/**
 * iucv_pathid_table: an array of *handler pointing into
 *                    iucv_handler_table for fast indexing by pathid;
 */
static handler **iucv_pathid_table;

static unsigned long max_connections;

/**
 * iucv_cpuid: contains the logical cpu number of the cpu which
 * has declared the iucv buffer by issuing DECLARE_BUFFER.
 * If no cpu has done the initialization iucv_cpuid contains -1.
 */
static int iucv_cpuid = -1;
/**
 * register_flag: is 0 when external interrupt has not been registered
 */
static int register_flag;

/****************FIVE 40-BYTE PARAMETER STRUCTURES******************/
/* Data struct 1: iparml_control
 * Used for iucv_accept
 *          iucv_connect
 *          iucv_quiesce
 *          iucv_resume
 *          iucv_sever
 *          iucv_retrieve_buffer
 * Data struct 2: iparml_dpl     (data in parameter list)
 * Used for iucv_send_prmmsg
 *          iucv_send2way_prmmsg
 *          iucv_send2way_prmmsg_array
 *          iucv_reply_prmmsg
 * Data struct 3: iparml_db       (data in a buffer)
 * Used for iucv_receive
 *          iucv_receive_array
 *          iucv_reject
 *          iucv_reply
 *          iucv_reply_array
 *          iucv_send
 *          iucv_send_array
 *          iucv_send2way
 *          iucv_send2way_array
 *          iucv_declare_buffer
 * Data struct 4: iparml_purge
 * Used for iucv_purge
 *          iucv_query
 * Data struct 5: iparml_set_mask
 * Used for iucv_set_mask
 */

typedef struct {
	__u16 ippathid;
	__u8  ipflags1;
	__u8  iprcode;
	__u16 ipmsglim;
	__u16 res1;
	__u8  ipvmid[8];
	__u8  ipuser[16];
	__u8  iptarget[8];
} iparml_control;

typedef struct {
	__u16 ippathid;
	__u8  ipflags1;
	__u8  iprcode;
	__u32 ipmsgid;
	__u32 iptrgcls;
	__u8  iprmmsg[8];
	__u32 ipsrccls;
	__u32 ipmsgtag;
	__u32 ipbfadr2;
	__u32 ipbfln2f;
	__u32 res;
} iparml_dpl;

typedef struct {
	__u16 ippathid;
	__u8  ipflags1;
	__u8  iprcode;
	__u32 ipmsgid;
	__u32 iptrgcls;
	__u32 ipbfadr1;
	__u32 ipbfln1f;
	__u32 ipsrccls;
	__u32 ipmsgtag;
	__u32 ipbfadr2;
	__u32 ipbfln2f;
	__u32 res;
} iparml_db;

typedef struct {
	__u16 ippathid;
	__u8  ipflags1;
	__u8  iprcode;
	__u32 ipmsgid;
	__u8  ipaudit[3];
	__u8  res1[5];
	__u32 res2;
	__u32 ipsrccls;
	__u32 ipmsgtag;
	__u32 res3[3];
} iparml_purge;

typedef struct {
	__u8  ipmask;
	__u8  res1[2];
	__u8  iprcode;
	__u32 res2[9];
} iparml_set_mask;

typedef struct {
	union {
		iparml_control  p_ctrl;
		iparml_dpl      p_dpl;
		iparml_db       p_db;
		iparml_purge    p_purge;
		iparml_set_mask p_set_mask;
	} param;
	atomic_t in_use;
	__u32    res;
}  __attribute__ ((aligned(8))) iucv_param;
#define PARAM_POOL_SIZE (PAGE_SIZE / sizeof(iucv_param))

static iucv_param * iucv_param_pool;

MODULE_AUTHOR("(C) 2001 IBM Corp. by Fritz Elfert (felfert@millenux.com)");
MODULE_DESCRIPTION("Linux for S/390 IUCV lowlevel driver");
MODULE_LICENSE("GPL");

/*
 * Debugging stuff
 *******************************************************************************/


#ifdef DEBUG
static int debuglevel = 0;

module_param(debuglevel, int, 0);
MODULE_PARM_DESC(debuglevel,
 "Specifies the debug level (0=off ... 3=all)");

static void
iucv_dumpit(char *title, void *buf, int len)
{
	int i;
	__u8 *p = (__u8 *)buf;

	if (debuglevel < 3)
		return;

	printk(KERN_DEBUG "%s\n", title);
	printk("  ");
	for (i = 0; i < len; i++) {
		if (!(i % 16) && i != 0)
			printk ("\n  ");
		else if (!(i % 4) && i != 0)
			printk(" ");
		printk("%02X", *p++);
	}
	if (len % 16)
		printk ("\n");
	return;
}
#define iucv_debug(lvl, fmt, args...) \
do { \
	if (debuglevel >= lvl) \
		printk(KERN_DEBUG "%s: " fmt "\n", __FUNCTION__ , ## args); \
} while (0)

#else

#define iucv_debug(lvl, fmt, args...)
#define iucv_dumpit(title, buf, len)

#endif

/*
 * Internal functions
 *******************************************************************************/

/**
 * print start banner
 */
static void
iucv_banner(void)
{
	printk(KERN_INFO "IUCV lowlevel driver initialized\n");
}

/**
 * iucv_init - Initialization
 *
 * Allocates and initializes various data structures.
 */
static int
iucv_init(void)
{
	int ret;

	if (iucv_external_int_buffer)
		return 0;

	if (!MACHINE_IS_VM) {
		printk(KERN_ERR "IUCV: IUCV connection needs VM as base\n");
		return -EPROTONOSUPPORT;
	}

	ret = bus_register(&iucv_bus);
	if (ret) {
		printk(KERN_ERR "IUCV: failed to register bus.\n");
		return ret;
	}

	iucv_root = s390_root_dev_register("iucv");
	if (IS_ERR(iucv_root)) {
		printk(KERN_ERR "IUCV: failed to register iucv root.\n");
		bus_unregister(&iucv_bus);
		return PTR_ERR(iucv_root);
	}

	/* Note: GFP_DMA used used to get memory below 2G */
	iucv_external_int_buffer = kzalloc(sizeof(iucv_GeneralInterrupt),
					   GFP_KERNEL|GFP_DMA);
	if (!iucv_external_int_buffer) {
		printk(KERN_WARNING
		       "%s: Could not allocate external interrupt buffer\n",
		       __FUNCTION__);
		s390_root_dev_unregister(iucv_root);
		bus_unregister(&iucv_bus);
		return -ENOMEM;
	}

	/* Initialize parameter pool */
	iucv_param_pool = kzalloc(sizeof(iucv_param) * PARAM_POOL_SIZE,
				  GFP_KERNEL|GFP_DMA);
	if (!iucv_param_pool) {
		printk(KERN_WARNING "%s: Could not allocate param pool\n",
		       __FUNCTION__);
		kfree(iucv_external_int_buffer);
		iucv_external_int_buffer = NULL;
		s390_root_dev_unregister(iucv_root);
		bus_unregister(&iucv_bus);
		return -ENOMEM;
	}

	/* Initialize irq queue */
	INIT_LIST_HEAD(&iucv_irq_queue);

	/* Initialize handler table */
	INIT_LIST_HEAD(&iucv_handler_table);

	iucv_banner();
	return 0;
}

/**
 * iucv_exit - De-Initialization
 *
 * Frees everything allocated from iucv_init.
 */
static int iucv_retrieve_buffer (void);

static void
iucv_exit(void)
{
	iucv_retrieve_buffer();
	kfree(iucv_external_int_buffer);
	iucv_external_int_buffer = NULL;
	kfree(iucv_param_pool);
	iucv_param_pool = NULL;
	s390_root_dev_unregister(iucv_root);
	bus_unregister(&iucv_bus);
	printk(KERN_INFO "IUCV lowlevel driver unloaded\n");
}

/**
 * grab_param: - Get a parameter buffer from the pre-allocated pool.
 *
 * This function searches for an unused element in the pre-allocated pool
 * of parameter buffers. If one is found, it marks it "in use" and returns
 * a pointer to it. The calling function is responsible for releasing it
 * when it has finished its usage.
 *
 * Returns: A pointer to iucv_param.
 */
static __inline__ iucv_param *
grab_param(void)
{
	iucv_param *ptr;
        static int hint = 0;

	ptr = iucv_param_pool + hint;
	do {
		ptr++;
		if (ptr >= iucv_param_pool + PARAM_POOL_SIZE)
			ptr = iucv_param_pool;
	} while (atomic_cmpxchg(&ptr->in_use, 0, 1) != 0);
	hint = ptr - iucv_param_pool;

	memset(&ptr->param, 0, sizeof(ptr->param));
	return ptr;
}

/**
 * release_param - Release a parameter buffer.
 * @p: A pointer to a struct iucv_param, previously obtained by calling
 *     grab_param().
 *
 * This function marks the specified parameter buffer "unused".
 */
static __inline__ void
release_param(void *p)
{
	atomic_set(&((iucv_param *)p)->in_use, 0);
}

/**
 * iucv_add_handler: - Add a new handler
 * @new_handler: handle that is being entered into chain.
 *
 * Places new handle on iucv_handler_table, if identical handler is not
 * found.
 *
 * Returns: 0 on success, !0 on failure (handler already in chain).
 */
static int
iucv_add_handler (handler *new)
{
	ulong flags;

	iucv_debug(1, "entering");
	iucv_dumpit("handler:", new, sizeof(handler));

	spin_lock_irqsave (&iucv_lock, flags);
	if (!list_empty(&iucv_handler_table)) {
		struct list_head *lh;

		/**
		 * Search list for handler with identical id. If one
		 * is found, the new handler is _not_ added.
		 */
		list_for_each(lh, &iucv_handler_table) {
			handler *h = list_entry(lh, handler, list);
			if (!memcmp(&new->id, &h->id, sizeof(h->id))) {
				iucv_debug(1, "ret 1");
				spin_unlock_irqrestore (&iucv_lock, flags);
				return 1;
			}
		}
	}
	/**
	 * If we get here, no handler was found.
	 */
	INIT_LIST_HEAD(&new->list);
	list_add(&new->list, &iucv_handler_table);
	spin_unlock_irqrestore (&iucv_lock, flags);

	iucv_debug(1, "exiting");
	return 0;
}

/**
 * b2f0:
 * @code: identifier of IUCV call to CP.
 * @parm: pointer to 40 byte iparml area passed to CP
 *
 * Calls CP to execute IUCV commands.
 *
 * Returns: return code from CP's IUCV call
 */
static __inline__ ulong
b2f0(__u32 code, void *parm)
{
	iucv_dumpit("iparml before b2f0 call:", parm, sizeof(iucv_param));

	asm volatile (
		"LRA   1,0(%1)\n\t"
		"LR    0,%0\n\t"
		".long 0xb2f01000"
		:
		: "d" (code), "a" (parm)
		: "0", "1"
		);

	iucv_dumpit("iparml after b2f0 call:", parm, sizeof(iucv_param));

	return (unsigned long)*((__u8 *)(parm + 3));
}

/*
 * Name: iucv_add_pathid
 * Purpose: Adds a path id to the system.
 * Input: pathid -  pathid that is going to be entered into system
 *        handle -  address of handler that the pathid will be associated
 *		   with.
 *        pgm_data - token passed in by application.
 * Output: 0: successful addition of pathid
 *	   - EINVAL - pathid entry is being used by another application
 *	   - ENOMEM - storage allocation for a new pathid table failed
*/
static int
__iucv_add_pathid(__u16 pathid, handler *handler)
{

	iucv_debug(1, "entering");

	iucv_debug(1, "handler is pointing to %p", handler);

	if (pathid > (max_connections - 1))
		return -EINVAL;

	if (iucv_pathid_table[pathid]) {
		iucv_debug(1, "pathid entry is %p", iucv_pathid_table[pathid]);
		printk(KERN_WARNING
		       "%s: Pathid being used, error.\n", __FUNCTION__);
		return -EINVAL;
	}
	iucv_pathid_table[pathid] = handler;

	iucv_debug(1, "exiting");
	return 0;
}				/* end of add_pathid function */

static int
iucv_add_pathid(__u16 pathid, handler *handler)
{
	ulong flags;
	int rc;

	spin_lock_irqsave (&iucv_lock, flags);
	rc = __iucv_add_pathid(pathid, handler);
	spin_unlock_irqrestore (&iucv_lock, flags);
	return rc;
}

static void
iucv_remove_pathid(__u16 pathid)
{
	ulong flags;

	if (pathid > (max_connections - 1))
		return;

	spin_lock_irqsave (&iucv_lock, flags);
	iucv_pathid_table[pathid] = NULL;
	spin_unlock_irqrestore (&iucv_lock, flags);
}

/**
 * iucv_declare_buffer_cpuid
 * Register at VM for subsequent IUCV operations. This is executed
 * on the reserved CPU iucv_cpuid. Called from iucv_declare_buffer().
 */
static void
iucv_declare_buffer_cpuid (void *result)
{
	iparml_db *parm;

	parm = (iparml_db *)grab_param();
	parm->ipbfadr1 = virt_to_phys(iucv_external_int_buffer);
	if ((*((ulong *)result) = b2f0(DECLARE_BUFFER, parm)) == 1)
		*((ulong *)result) = parm->iprcode;
	release_param(parm);
}

/**
 * iucv_retrieve_buffer_cpuid:
 * Unregister IUCV usage at VM. This is always executed on the same
 * cpu that registered the buffer to VM.
 * Called from iucv_retrieve_buffer().
 */
static void
iucv_retrieve_buffer_cpuid (void *cpu)
{
	iparml_control *parm;

	parm = (iparml_control *)grab_param();
	b2f0(RETRIEVE_BUFFER, parm);
	release_param(parm);
}

/**
 * Name: iucv_declare_buffer
 * Purpose: Specifies the guests real address of an external
 *          interrupt.
 * Input: void
 * Output: iprcode - return code from b2f0 call
 */
static int
iucv_declare_buffer (void)
{
	unsigned long flags;
	ulong b2f0_result;

	iucv_debug(1, "entering");
	b2f0_result = -ENODEV;
	spin_lock_irqsave (&iucv_lock, flags);
	if (iucv_cpuid == -1) {
		/* Reserve any cpu for use by iucv. */
		iucv_cpuid = smp_get_cpu(CPU_MASK_ALL);
		spin_unlock_irqrestore (&iucv_lock, flags);
		smp_call_function_on(iucv_declare_buffer_cpuid,
			&b2f0_result, 0, 1, iucv_cpuid);
		if (b2f0_result) {
			smp_put_cpu(iucv_cpuid);
			iucv_cpuid = -1;
		}
		iucv_debug(1, "Address of EIB = %p", iucv_external_int_buffer);
	} else {
		spin_unlock_irqrestore (&iucv_lock, flags);
		b2f0_result = 0;
	}
	iucv_debug(1, "exiting");
	return b2f0_result;
}

/**
 * iucv_retrieve_buffer:
 *
 * Terminates all use of IUCV.
 * Returns: return code from CP
 */
static int
iucv_retrieve_buffer (void)
{
	iucv_debug(1, "entering");
	if (iucv_cpuid != -1) {
		smp_call_function_on(iucv_retrieve_buffer_cpuid,
				     0, 0, 1, iucv_cpuid);
		/* Release the cpu reserved by iucv_declare_buffer. */
		smp_put_cpu(iucv_cpuid);
		iucv_cpuid = -1;
	}
	iucv_debug(1, "exiting");
	return 0;
}

/**
 * iucv_remove_handler:
 * @users_handler: handler to be removed
 *
 * Remove handler when application unregisters.
 */
static void
iucv_remove_handler(handler *handler)
{
	unsigned long flags;

	if ((!iucv_pathid_table) || (!handler))
		return;

	iucv_debug(1, "entering");

	spin_lock_irqsave (&iucv_lock, flags);
	list_del(&handler->list);
	if (list_empty(&iucv_handler_table)) {
		if (register_flag) {
			unregister_external_interrupt(0x4000, iucv_irq_handler);
			register_flag = 0;
		}
	}
	spin_unlock_irqrestore (&iucv_lock, flags);

	iucv_debug(1, "exiting");
	return;
}

/**
 * iucv_register_program:
 * @pgmname:  user identification
 * @userid:   machine identification
 * @pgmmask:  Indicates which bits in the pgmname and userid combined will be
 *            used to determine who is given control.
 * @ops:      Address of interrupt handler table.
 * @pgm_data: Application data to be passed to interrupt handlers.
 *
 * Registers an application with IUCV.
 * Returns:
 *           The address of handler, or NULL on failure.
 * NOTE on pgmmask:
 *   If pgmname, userid and pgmmask are provided, pgmmask is entered into the
 *   handler as is.
 *   If pgmmask is NULL, the internal mask is set to all 0xff's
 *   When userid is NULL, the first 8 bytes of the internal mask are forced
 *   to 0x00.
 *   If pgmmask and userid are NULL, the first 8 bytes of the internal mask
 *   are forced to 0x00 and the last 16 bytes to 0xff.
 */

iucv_handle_t
iucv_register_program (__u8 pgmname[16],
		       __u8 userid[8],
		       __u8 pgmmask[24],
		       iucv_interrupt_ops_t * ops, void *pgm_data)
{
	ulong rc = 0;		/* return code from function calls */
	handler *new_handler;

	iucv_debug(1, "entering");

	if (ops == NULL) {
		/* interrupt table is not defined */
		printk(KERN_WARNING "%s: Interrupt table is not defined, "
		       "exiting\n", __FUNCTION__);
		return NULL;
	}
	if (!pgmname) {
		printk(KERN_WARNING "%s: pgmname not provided\n", __FUNCTION__);
		return NULL;
	}

	/* Allocate handler entry */
	new_handler = (handler *)kmalloc(sizeof(handler), GFP_ATOMIC);
	if (new_handler == NULL) {
		printk(KERN_WARNING "%s: storage allocation for new handler "
		       "failed.\n", __FUNCTION__);
		return NULL;
	}

	if (!iucv_pathid_table) {
		if (iucv_init()) {
			kfree(new_handler);
			return NULL;
		}

		max_connections = iucv_query_maxconn();
		iucv_pathid_table = kcalloc(max_connections, sizeof(handler *),
					GFP_ATOMIC);
		if (iucv_pathid_table == NULL) {
			printk(KERN_WARNING "%s: iucv_pathid_table storage "
			       "allocation failed\n", __FUNCTION__);
			kfree(new_handler);
			return NULL;
		}
	}
	memset(new_handler, 0, sizeof (handler));
	memcpy(new_handler->id.user_data, pgmname,
		sizeof (new_handler->id.user_data));
	if (userid) {
		memcpy (new_handler->id.userid, userid,
			sizeof (new_handler->id.userid));
		ASCEBC (new_handler->id.userid,
			sizeof (new_handler->id.userid));
		EBC_TOUPPER (new_handler->id.userid,
			     sizeof (new_handler->id.userid));
		
		if (pgmmask) {
			memcpy (new_handler->id.mask, pgmmask,
				sizeof (new_handler->id.mask));
		} else {
			memset (new_handler->id.mask, 0xFF,
				sizeof (new_handler->id.mask));
		}
	} else {
		if (pgmmask) {
			memcpy (new_handler->id.mask, pgmmask,
				sizeof (new_handler->id.mask));
		} else {
			memset (new_handler->id.mask, 0xFF,
				sizeof (new_handler->id.mask));
		}
		memset (new_handler->id.userid, 0x00,
			sizeof (new_handler->id.userid));
	}
	/* fill in the rest of handler */
	new_handler->pgm_data = pgm_data;
	new_handler->interrupt_table = ops;

	/*
	 * Check if someone else is registered with same pgmname, userid
	 * and mask. If someone is already registered with same pgmname,
	 * userid and mask, registration will fail and NULL will be returned
	 * to the application.
	 * If identical handler not found, then handler is added to list.
	 */
	rc = iucv_add_handler(new_handler);
	if (rc) {
		printk(KERN_WARNING "%s: Someone already registered with same "
		       "pgmname, userid, pgmmask\n", __FUNCTION__);
		kfree (new_handler);
		return NULL;
	}

	rc = iucv_declare_buffer();
	if (rc) {
		char *err = "Unknown";
		iucv_remove_handler(new_handler);
		kfree(new_handler);
		switch(rc) {
		case 0x03:
			err = "Directory error";
			break;
		case 0x0a:
			err = "Invalid length";
			break;
		case 0x13:
			err = "Buffer already exists";
			break;
		case 0x3e:
			err = "Buffer overlap";
			break;
		case 0x5c:
			err = "Paging or storage error";
			break;
		}
		printk(KERN_WARNING "%s: iucv_declare_buffer "
		       "returned error 0x%02lx (%s)\n", __FUNCTION__, rc, err);
		return NULL;
	}
	if (!register_flag) {
		/* request the 0x4000 external interrupt */
		rc = register_external_interrupt (0x4000, iucv_irq_handler);
		if (rc) {
			iucv_remove_handler(new_handler);
			kfree (new_handler);
			printk(KERN_WARNING "%s: "
			       "register_external_interrupt returned %ld\n",
			       __FUNCTION__, rc);
			return NULL;

		}
		register_flag = 1;
	}
	iucv_debug(1, "exiting");
	return new_handler;
}				/* end of register function */

/**
 * iucv_unregister_program:
 * @handle: address of handler
 *
 * Unregister application with IUCV.
 * Returns:
 *   0 on success, -EINVAL, if specified handle is invalid.
 */

int
iucv_unregister_program (iucv_handle_t handle)
{
	handler *h = NULL;
	struct list_head *lh;
	int i;
	ulong flags;

	iucv_debug(1, "entering");
	iucv_debug(1, "address of handler is %p", h);

	/* Checking if handle is valid  */
	spin_lock_irqsave (&iucv_lock, flags);
	list_for_each(lh, &iucv_handler_table) {
		if ((handler *)handle == list_entry(lh, handler, list)) {
			h = (handler *)handle;
			break;
		}
	}
	if (!h) {
		spin_unlock_irqrestore (&iucv_lock, flags);
		if (handle)
			printk(KERN_WARNING
			       "%s: Handler not found in iucv_handler_table.\n",
			       __FUNCTION__);
		else
			printk(KERN_WARNING
			       "%s: NULL handle passed by application.\n",
			       __FUNCTION__);
		return -EINVAL;
	}

	/**
	 * First, walk thru iucv_pathid_table and sever any pathid which is
	 * still pointing to the handler to be removed.
	 */
	for (i = 0; i < max_connections; i++)
		if (iucv_pathid_table[i] == h) {
			spin_unlock_irqrestore (&iucv_lock, flags);
			iucv_sever(i, h->id.user_data);
			spin_lock_irqsave(&iucv_lock, flags);
		}
	spin_unlock_irqrestore (&iucv_lock, flags);

	iucv_remove_handler(h);
	kfree(h);

	iucv_debug(1, "exiting");
	return 0;
}

/**
 * iucv_accept:
 * @pathid:             Path identification number
 * @msglim_reqstd:      The number of outstanding messages requested.
 * @user_data:          Data specified by the iucv_connect function.
 * @flags1:             Contains options for this path.
 *     - IPPRTY (0x20)   Specifies if you want to send priority message.
 *     - IPRMDATA (0x80) Specifies whether your program can handle a message
 *                       in the parameter list.
 *     - IPQUSCE (0x40)  Specifies whether you want to quiesce the path being
 *		         established.
 * @handle:             Address of handler.
 * @pgm_data:           Application data passed to interrupt handlers.
 * @flags1_out:         Pointer to an int. If not NULL, on return the options for
 *                      the path are stored at the given location:
 *     - IPPRTY (0x20)  Indicates you may send a priority message.
 * @msglim:             Pointer to an __u16. If not NULL, on return the maximum
 *                      number of outstanding messages is stored at the given
 *                      location.
 *
 * This function is issued after the user receives a Connection Pending external
 * interrupt and now wishes to complete the IUCV communication path.
 * Returns:
 *   return code from CP
 */
int
iucv_accept(__u16 pathid, __u16 msglim_reqstd,
	     __u8 user_data[16], int flags1,
	     iucv_handle_t handle, void *pgm_data,
	     int *flags1_out, __u16 * msglim)
{
	ulong b2f0_result = 0;
	ulong flags;
	struct list_head *lh;
	handler *h = NULL;
	iparml_control *parm;

	iucv_debug(1, "entering");
	iucv_debug(1, "pathid = %d", pathid);

	/* Checking if handle is valid  */
	spin_lock_irqsave (&iucv_lock, flags);
	list_for_each(lh, &iucv_handler_table) {
		if ((handler *)handle == list_entry(lh, handler, list)) {
			h = (handler *)handle;
			break;
		}
	}
	spin_unlock_irqrestore (&iucv_lock, flags);

	if (!h) {
		if (handle)
			printk(KERN_WARNING
			       "%s: Handler not found in iucv_handler_table.\n",
			       __FUNCTION__);
		else
			printk(KERN_WARNING
			       "%s: NULL handle passed by application.\n",
			       __FUNCTION__);
		return -EINVAL;
	}

	parm = (iparml_control *)grab_param();

	parm->ippathid = pathid;
	parm->ipmsglim = msglim_reqstd;
	if (user_data)
		memcpy(parm->ipuser, user_data, sizeof(parm->ipuser));

	parm->ipflags1 = (__u8)flags1;
	b2f0_result = b2f0(ACCEPT, parm);

	if (!b2f0_result) {
		if (msglim)
			*msglim = parm->ipmsglim;
		if (pgm_data)
			h->pgm_data = pgm_data;
		if (flags1_out)
			*flags1_out = (parm->ipflags1 & IPPRTY) ? IPPRTY : 0;
	}
	release_param(parm);

	iucv_debug(1, "exiting");
	return b2f0_result;
}

/**
 * iucv_connect:
 * @pathid:        Path identification number
 * @msglim_reqstd: Number of outstanding messages requested
 * @user_data:     16-byte user data
 * @userid:        8-byte of user identification
 * @system_name:   8-byte identifying the system name
 * @flags1:        Specifies options for this path:
 *     - IPPRTY (0x20)   Specifies if you want to send priority message.
 *     - IPRMDATA (0x80) Specifies whether your program can handle a message
 *                       in  the parameter list.
 *     - IPQUSCE (0x40)  Specifies whether you want to quiesce the path being
 *                       established.
 *     - IPLOCAL (0x01)  Allows an application to force the partner to be on the
 *                       local system. If local is specified then target class
 *                       cannot be specified.
 * @flags1_out:    Pointer to an int. If not NULL, on return the options for
 *                 the path are stored at the given location:
 *     - IPPRTY (0x20)   Indicates you may send a priority message.
 * @msglim:        Pointer to an __u16. If not NULL, on return the maximum
 *                 number of outstanding messages is stored at the given
 *                 location.
 * @handle:        Address of handler.
 * @pgm_data:      Application data to be passed to interrupt handlers.
 *
 * This function establishes an IUCV path. Although the connect may complete
 * successfully, you are not able to use the path until you receive an IUCV
 * Connection Complete external interrupt.
 * Returns: return code from CP, or one of the following
 *     - ENOMEM
 *     - return code from iucv_declare_buffer
 *     - EINVAL - invalid handle passed by application
 *     - EINVAL - pathid address is NULL
 *     - ENOMEM - pathid table storage allocation failed
 *     - return code from internal function add_pathid
 */
int
iucv_connect (__u16 *pathid, __u16 msglim_reqstd,
	      __u8 user_data[16], __u8 userid[8],
	      __u8 system_name[8], int flags1,
	      int *flags1_out, __u16 * msglim,
	      iucv_handle_t handle, void *pgm_data)
{
	iparml_control *parm;
	iparml_control local_parm;
	struct list_head *lh;
	ulong b2f0_result = 0;
	ulong flags;
	int add_pathid_result = 0;
	handler *h = NULL;
	__u8 no_memory[16] = "NO MEMORY";

	iucv_debug(1, "entering");

	/* Checking if handle is valid  */
	spin_lock_irqsave (&iucv_lock, flags);
	list_for_each(lh, &iucv_handler_table) {
		if ((handler *)handle == list_entry(lh, handler, list)) {
			h = (handler *)handle;
			break;
		}
	}
	spin_unlock_irqrestore (&iucv_lock, flags);

	if (!h) {
		if (handle)
			printk(KERN_WARNING
			       "%s: Handler not found in iucv_handler_table.\n",
			       __FUNCTION__);
		else
			printk(KERN_WARNING
			       "%s: NULL handle passed by application.\n",
			       __FUNCTION__);
		return -EINVAL;
	}

	if (pathid == NULL) {
		printk(KERN_WARNING "%s: NULL pathid pointer\n",
		       __FUNCTION__);
		return -EINVAL;
	}

	parm = (iparml_control *)grab_param();

	parm->ipmsglim = msglim_reqstd;

	if (user_data)
		memcpy(parm->ipuser, user_data, sizeof(parm->ipuser));

	if (userid) {
		memcpy(parm->ipvmid, userid, sizeof(parm->ipvmid));
		ASCEBC(parm->ipvmid, sizeof(parm->ipvmid));
		EBC_TOUPPER(parm->ipvmid, sizeof(parm->ipvmid));
	}

	if (system_name) {
		memcpy(parm->iptarget, system_name, sizeof(parm->iptarget));
		ASCEBC(parm->iptarget, sizeof(parm->iptarget));
		EBC_TOUPPER(parm->iptarget, sizeof(parm->iptarget));
	}

	/* In order to establish an IUCV connection, the procedure is:
         *
         * b2f0(CONNECT)
         * take the ippathid from the b2f0 call
         * register the handler to the ippathid
         *
         * Unfortunately, the ConnectionEstablished message gets sent after the
         * b2f0(CONNECT) call but before the register is handled.
         *
         * In order for this race condition to be eliminated, the IUCV Control
         * Interrupts must be disabled for the above procedure.
         *
         * David Kennedy <dkennedy@linuxcare.com>
         */

	/* Enable everything but IUCV Control messages */
	iucv_setmask(~(AllInterrupts));
	messagesDisabled = 1;

	spin_lock_irqsave (&iucv_lock, flags);
	parm->ipflags1 = (__u8)flags1;
	b2f0_result = b2f0(CONNECT, parm);
	memcpy(&local_parm, parm, sizeof(local_parm));
	release_param(parm);
	parm = &local_parm;
	if (!b2f0_result)
		add_pathid_result = __iucv_add_pathid(parm->ippathid, h);
	spin_unlock_irqrestore (&iucv_lock, flags);

	if (b2f0_result) {
		iucv_setmask(~0);
		messagesDisabled = 0;
		return b2f0_result;
	}

	*pathid = parm->ippathid;

	/* Enable everything again */
	iucv_setmask(IUCVControlInterruptsFlag);

	if (msglim)
		*msglim = parm->ipmsglim;
	if (flags1_out)
		*flags1_out = (parm->ipflags1 & IPPRTY) ? IPPRTY : 0;

	if (add_pathid_result) {
		iucv_sever(*pathid, no_memory);
		printk(KERN_WARNING "%s: add_pathid failed with rc ="
			" %d\n", __FUNCTION__, add_pathid_result);
		return(add_pathid_result);
	}

	iucv_debug(1, "exiting");
	return b2f0_result;
}

/**
 * iucv_purge:
 * @pathid: Path identification number
 * @msgid:  Message ID of message to purge.
 * @srccls: Message class of the message to purge.
 * @audit:  Pointer to an __u32. If not NULL, on return, information about
 *          asynchronous errors that may have affected the normal completion
 *          of this message ist stored at the given location.
 *
 * Cancels a message you have sent.
 * Returns: return code from CP
 */
int
iucv_purge (__u16 pathid, __u32 msgid, __u32 srccls, __u32 *audit)
{
	iparml_purge *parm;
	ulong b2f0_result = 0;

	iucv_debug(1, "entering");
	iucv_debug(1, "pathid = %d", pathid);

	parm = (iparml_purge *)grab_param();

	parm->ipmsgid = msgid;
	parm->ippathid = pathid;
	parm->ipsrccls = srccls;
	parm->ipflags1 |= (IPSRCCLS | IPFGMID | IPFGPID);
	b2f0_result = b2f0(PURGE, parm);

	if (!b2f0_result && audit) {
		memcpy(audit, parm->ipaudit, sizeof(parm->ipaudit));
		/* parm->ipaudit has only 3 bytes */
		*audit >>= 8;
	}
	
	release_param(parm);

	iucv_debug(1, "b2f0_result = %ld", b2f0_result);
	iucv_debug(1, "exiting");
	return b2f0_result;
}

/**
 * iucv_query_generic:
 * @want_maxconn: Flag, describing which value is to be returned.
 *
 * Helper function for iucv_query_maxconn() and iucv_query_bufsize().
 *
 * Returns: The buffersize, if want_maxconn is 0; the maximum number of
 *           connections, if want_maxconn is 1 or an error-code < 0 on failure.
 */
static int
iucv_query_generic(int want_maxconn)
{
	iparml_purge *parm = (iparml_purge *)grab_param();
	int bufsize, maxconn;
	int ccode;

	/**
	 * Call b2f0 and store R0 (max buffer size),
	 * R1 (max connections) and CC.
	 */
	asm volatile (
		"LRA   1,0(%4)\n\t"
		"LR    0,%3\n\t"
		".long 0xb2f01000\n\t"
		"IPM   %0\n\t"
		"SRL   %0,28\n\t"
		"ST    0,%1\n\t"
		"ST    1,%2\n\t"
		: "=d" (ccode), "=m" (bufsize), "=m" (maxconn)
		: "d" (QUERY), "a" (parm)
		: "0", "1", "cc"
		);
	release_param(parm);

	if (ccode)
		return -EPERM;
	if (want_maxconn)
		return maxconn;
	return bufsize;
}

/**
 * iucv_query_maxconn:
 *
 * Determines the maximum number of connections thay may be established.
 *
 * Returns: Maximum number of connections that can be.
 */
ulong
iucv_query_maxconn(void)
{
	return iucv_query_generic(1);
}

/**
 * iucv_query_bufsize:
 *
 * Determines the size of the external interrupt buffer.
 *
 * Returns: Size of external interrupt buffer.
 */
ulong
iucv_query_bufsize (void)
{
	return iucv_query_generic(0);
}

/**
 * iucv_quiesce:
 * @pathid:    Path identification number
 * @user_data: 16-byte user data
 *
 * Temporarily suspends incoming messages on an IUCV path.
 * You can later reactivate the path by invoking the iucv_resume function.
 * Returns: return code from CP
 */
int
iucv_quiesce (__u16 pathid, __u8 user_data[16])
{
	iparml_control *parm;
	ulong b2f0_result = 0;

	iucv_debug(1, "entering");
	iucv_debug(1, "pathid = %d", pathid);

	parm = (iparml_control *)grab_param();

	memcpy(parm->ipuser, user_data, sizeof(parm->ipuser));
	parm->ippathid = pathid;

	b2f0_result = b2f0(QUIESCE, parm);
	release_param(parm);

	iucv_debug(1, "b2f0_result = %ld", b2f0_result);
	iucv_debug(1, "exiting");

	return b2f0_result;
}

/**
 * iucv_receive:
 * @pathid: Path identification number.
 * @buffer: Address of buffer to receive. Must be below 2G.
 * @buflen: Length of buffer to receive.
 * @msgid:  Specifies the message ID.
 * @trgcls: Specifies target class.
 * @flags1_out: Receives options for path on return.
 *    - IPNORPY (0x10)  Specifies whether a reply is required
 *    - IPPRTY (0x20)   Specifies if you want to send priority message
 *    - IPRMDATA (0x80) Specifies the data is contained in the parameter list
 * @residual_buffer: Receives the address of buffer updated by the number
 *                   of bytes you have received on return.
 * @residual_length: On return, receives one of the following values:
 *    - 0                          If the receive buffer is the same length as
 *                                 the message.
 *    - Remaining bytes in buffer  If the receive buffer is longer than the
 *                                 message.
 *    - Remaining bytes in message If the receive buffer is shorter than the
 *                                 message.
 *
 * This function receives messages that are being sent to you over established
 * paths.
 * Returns: return code from CP IUCV call; If the receive buffer is shorter
 *   than the message, always 5
 *   -EINVAL - buffer address is pointing to NULL
 */
int
iucv_receive (__u16 pathid, __u32 msgid, __u32 trgcls,
	      void *buffer, ulong buflen,
	      int *flags1_out, ulong * residual_buffer, ulong * residual_length)
{
	iparml_db *parm;
	ulong b2f0_result;
	int moved = 0;	/* number of bytes moved from parmlist to buffer */

	iucv_debug(2, "entering");

	if (!buffer)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ipbfadr1 = (__u32) (addr_t) buffer;
	parm->ipbfln1f = (__u32) ((ulong) buflen);
	parm->ipmsgid = msgid;
	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipflags1 = (IPFGPID | IPFGMID | IPFGMCL);

	b2f0_result = b2f0(RECEIVE, parm);

	if (!b2f0_result || b2f0_result == 5) {
		if (flags1_out) {
			iucv_debug(2, "*flags1_out = %d", *flags1_out);
			*flags1_out = (parm->ipflags1 & (~0x07));
			iucv_debug(2, "*flags1_out = %d", *flags1_out);
		}

		if (!(parm->ipflags1 & IPRMDATA)) {	/*msg not in parmlist */
			if (residual_length)
				*residual_length = parm->ipbfln1f;

			if (residual_buffer)
				*residual_buffer = parm->ipbfadr1;
		} else {
			moved = min_t (unsigned long, buflen, 8);

			memcpy ((char *) buffer,
				(char *) &parm->ipbfadr1, moved);

			if (buflen < 8)
				b2f0_result = 5;

			if (residual_length)
				*residual_length = abs (buflen - 8);

			if (residual_buffer)
				*residual_buffer = (ulong) (buffer + moved);
		}
	}
	release_param(parm);

	iucv_debug(2, "exiting");
	return b2f0_result;
}

/*
 * Name: iucv_receive_array
 * Purpose: This function receives messages that are being sent to you
 *          over established paths.
 * Input: pathid - path identification number
 *        buffer - address of array of buffers
 *        buflen - total length of buffers
 *        msgid - specifies the message ID.
 *        trgcls - specifies target class
 * Output:
 *        flags1_out: Options for path.
 *          IPNORPY - 0x10 specifies whether a reply is required
 *          IPPRTY - 0x20 specifies if you want to send priority message
 *         IPRMDATA - 0x80 specifies the data is contained in the parameter list
 *       residual_buffer - address points to the current list entry IUCV
 *                         is working on.
 *       residual_length -
 *              Contains one of the following values, if the receive buffer is:
 *               The same length as the message, this field is zero.
 *               Longer than the message, this field contains the number of
 *                bytes remaining in the buffer.
 *               Shorter than the message, this field contains the residual
 *                count (that is, the number of bytes remaining in the
 *                message that does not fit into the buffer. In this case
 *		  b2f0_result = 5.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - buffer address is NULL
 */
int
iucv_receive_array (__u16 pathid,
		    __u32 msgid, __u32 trgcls,
		    iucv_array_t * buffer, ulong buflen,
		    int *flags1_out,
		    ulong * residual_buffer, ulong * residual_length)
{
	iparml_db *parm;
	ulong b2f0_result;
	int i = 0, moved = 0, need_to_move = 8, dyn_len;

	iucv_debug(2, "entering");

	if (!buffer)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ipbfadr1 = (__u32) ((ulong) buffer);
	parm->ipbfln1f = (__u32) buflen;
	parm->ipmsgid = msgid;
	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipflags1 = (IPBUFLST | IPFGPID | IPFGMID | IPFGMCL);

	b2f0_result = b2f0(RECEIVE, parm);

	if (!b2f0_result || b2f0_result == 5) {

		if (flags1_out) {
			iucv_debug(2, "*flags1_out = %d", *flags1_out);
			*flags1_out = (parm->ipflags1 & (~0x07));
			iucv_debug(2, "*flags1_out = %d", *flags1_out);
		}

		if (!(parm->ipflags1 & IPRMDATA)) {	/*msg not in parmlist */

			if (residual_length)
				*residual_length = parm->ipbfln1f;

			if (residual_buffer)
				*residual_buffer = parm->ipbfadr1;

		} else {
			/* copy msg from parmlist to users array. */

			while ((moved < 8) && (moved < buflen)) {
				dyn_len =
				    min_t (unsigned int,
					 (buffer + i)->length, need_to_move);

				memcpy ((char *)((ulong)((buffer + i)->address)),
					((char *) &parm->ipbfadr1) + moved,
					dyn_len);

				moved += dyn_len;
				need_to_move -= dyn_len;

				(buffer + i)->address =
				    	(__u32)
				((ulong)(__u8 *) ((ulong)(buffer + i)->address)
						+ dyn_len);

				(buffer + i)->length -= dyn_len;
				i++;
			}

			if (need_to_move)	/* buflen < 8 bytes */
				b2f0_result = 5;

			if (residual_length)
				*residual_length = abs (buflen - 8);

			if (residual_buffer) {
				if (!moved)
					*residual_buffer = (ulong) buffer;
				else
					*residual_buffer =
					    (ulong) (buffer + (i - 1));
			}

		}
	}
	release_param(parm);

	iucv_debug(2, "exiting");
	return b2f0_result;
}

/**
 * iucv_reject:
 * @pathid: Path identification number.
 * @msgid:  Message ID of the message to reject.
 * @trgcls: Target class of the message to reject.
 * Returns: return code from CP
 *
 * Refuses a specified message. Between the time you are notified of a
 * message and the time that you complete the message, the message may
 * be rejected.
 */
int
iucv_reject (__u16 pathid, __u32 msgid, __u32 trgcls)
{
	iparml_db *parm;
	ulong b2f0_result = 0;

	iucv_debug(1, "entering");
	iucv_debug(1, "pathid = %d", pathid);

	parm = (iparml_db *)grab_param();

	parm->ippathid = pathid;
	parm->ipmsgid = msgid;
	parm->iptrgcls = trgcls;
	parm->ipflags1 = (IPFGMCL | IPFGMID | IPFGPID);

	b2f0_result = b2f0(REJECT, parm);
	release_param(parm);

	iucv_debug(1, "b2f0_result = %ld", b2f0_result);
	iucv_debug(1, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_reply
 * Purpose: This function responds to the two-way messages that you
 *          receive. You must identify completely the message to
 *          which you wish to reply. ie, pathid, msgid, and trgcls.
 * Input: pathid - path identification number
 *        msgid - specifies the message ID.
 *        trgcls - specifies target class
 *        flags1 - option for path
 *                 IPPRTY- 0x20 - specifies if you want to send priority message
 *        buffer - address of reply buffer
 *        buflen - length of reply buffer
 * Output: ipbfadr2 - Address of buffer updated by the number
 *                    of bytes you have moved.
 *         ipbfln2f - Contains one of the following values:
 *              If the answer buffer is the same length as the reply, this field
 *               contains zero.
 *              If the answer buffer is longer than the reply, this field contains
 *               the number of bytes remaining in the buffer.
 *              If the answer buffer is shorter than the reply, this field contains
 *               a residual count (that is, the number of bytes remianing in the
 *               reply that does not fit into the buffer. In this
 *                case b2f0_result = 5.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - buffer address is NULL
 */
int
iucv_reply (__u16 pathid,
	    __u32 msgid, __u32 trgcls,
	    int flags1,
	    void *buffer, ulong buflen, ulong * ipbfadr2, ulong * ipbfln2f)
{
	iparml_db *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!buffer)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ipbfadr2 = (__u32) ((ulong) buffer);
	parm->ipbfln2f = (__u32) buflen;	/* length of message */
	parm->ippathid = pathid;
	parm->ipmsgid = msgid;
	parm->iptrgcls = trgcls;
	parm->ipflags1 = (__u8) flags1;	/* priority message */

	b2f0_result = b2f0(REPLY, parm);

	if ((!b2f0_result) || (b2f0_result == 5)) {
		if (ipbfadr2)
			*ipbfadr2 = parm->ipbfadr2;
		if (ipbfln2f)
			*ipbfln2f = parm->ipbfln2f;
	}
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_reply_array
 * Purpose: This function responds to the two-way messages that you
 *          receive. You must identify completely the message to
 *          which you wish to reply. ie, pathid, msgid, and trgcls.
 *          The array identifies a list of addresses and lengths of
 *          discontiguous buffers that contains the reply data.
 * Input: pathid - path identification number
 *        msgid - specifies the message ID.
 *        trgcls - specifies target class
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        buffer - address of array of reply buffers
 *        buflen - total length of reply buffers
 * Output: ipbfadr2 - Address of buffer which IUCV is currently working on.
 *         ipbfln2f - Contains one of the following values:
 *              If the answer buffer is the same length as the reply, this field
 *               contains zero.
 *              If the answer buffer is longer than the reply, this field contains
 *               the number of bytes remaining in the buffer.
 *              If the answer buffer is shorter than the reply, this field contains
 *               a residual count (that is, the number of bytes remianing in the
 *               reply that does not fit into the buffer. In this
 *               case b2f0_result = 5.
 * Return: b2f0_result - return code from CP
 *             (-EINVAL) - buffer address is NULL
*/
int
iucv_reply_array (__u16 pathid,
		  __u32 msgid, __u32 trgcls,
		  int flags1,
		  iucv_array_t * buffer,
		  ulong buflen, ulong * ipbfadr2, ulong * ipbfln2f)
{
	iparml_db *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!buffer)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ipbfadr2 = (__u32) ((ulong) buffer);
	parm->ipbfln2f = buflen;	/* length of message */
	parm->ippathid = pathid;
	parm->ipmsgid = msgid;
	parm->iptrgcls = trgcls;
	parm->ipflags1 = (IPANSLST | flags1);

	b2f0_result = b2f0(REPLY, parm);

	if ((!b2f0_result) || (b2f0_result == 5)) {

		if (ipbfadr2)
			*ipbfadr2 = parm->ipbfadr2;
		if (ipbfln2f)
			*ipbfln2f = parm->ipbfln2f;
	}
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_reply_prmmsg
 * Purpose: This function responds to the two-way messages that you
 *          receive. You must identify completely the message to
 *          which you wish to reply. ie, pathid, msgid, and trgcls.
 *          Prmmsg signifies the data is moved into the
 *          parameter list.
 * Input: pathid - path identification number
 *        msgid - specifies the message ID.
 *        trgcls - specifies target class
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        prmmsg - 8-bytes of data to be placed into the parameter
 *                 list.
 * Output: NA
 * Return: b2f0_result - return code from CP
*/
int
iucv_reply_prmmsg (__u16 pathid,
		   __u32 msgid, __u32 trgcls, int flags1, __u8 prmmsg[8])
{
	iparml_dpl *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	parm = (iparml_dpl *)grab_param();

	parm->ippathid = pathid;
	parm->ipmsgid = msgid;
	parm->iptrgcls = trgcls;
	memcpy(parm->iprmmsg, prmmsg, sizeof (parm->iprmmsg));
	parm->ipflags1 = (IPRMDATA | flags1);

	b2f0_result = b2f0(REPLY, parm);
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/**
 * iucv_resume:
 * @pathid:    Path identification number
 * @user_data: 16-byte of user data
 *
 * This function restores communication over a quiesced path.
 * Returns: return code from CP
 */
int
iucv_resume (__u16 pathid, __u8 user_data[16])
{
	iparml_control *parm;
	ulong b2f0_result = 0;

	iucv_debug(1, "entering");
	iucv_debug(1, "pathid = %d", pathid);

	parm = (iparml_control *)grab_param();

	memcpy (parm->ipuser, user_data, sizeof (*user_data));
	parm->ippathid = pathid;

	b2f0_result = b2f0(RESUME, parm);
	release_param(parm);

	iucv_debug(1, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_send
 * Purpose: sends messages
 * Input: pathid - ushort, pathid
 *        msgid  - ulong *, id of message returned to caller
 *        trgcls - ulong, target message class
 *        srccls - ulong, source message class
 *        msgtag - ulong, message tag
 *	  flags1  - Contains options for this path.
 *		IPPRTY - Ox20 - specifies if you want to send a priority message.
 *        buffer - pointer to buffer
 *        buflen - ulong, length of buffer
 * Output: b2f0_result - return code from b2f0 call
 *         msgid - returns message id
 */
int
iucv_send (__u16 pathid, __u32 * msgid,
	   __u32 trgcls, __u32 srccls,
	   __u32 msgtag, int flags1, void *buffer, ulong buflen)
{
	iparml_db *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!buffer)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ipbfadr1 = (__u32) ((ulong) buffer);
	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipbfln1f = (__u32) buflen;	/* length of message */
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipflags1 = (IPNORPY | flags1);	/* one way priority message */

	b2f0_result = b2f0(SEND, parm);

	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_send_array
 * Purpose: This function transmits data to another application.
 *          The contents of buffer is the address of the array of
 *          addresses and lengths of discontiguous buffers that hold
 *          the message text. This is a one-way message and the
 *          receiver will not reply to the message.
 * Input: pathid - path identification number
 *        trgcls - specifies target class
 *        srccls - specifies the source message class
 *        msgtag - specifies a tag to be associated witht the message
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        buffer - address of array of send buffers
 *        buflen - total length of send buffers
 * Output: msgid - specifies the message ID.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - buffer address is NULL
 */
int
iucv_send_array (__u16 pathid,
		 __u32 * msgid,
		 __u32 trgcls,
		 __u32 srccls,
		 __u32 msgtag, int flags1, iucv_array_t * buffer, ulong buflen)
{
	iparml_db *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!buffer)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipbfadr1 = (__u32) ((ulong) buffer);
	parm->ipbfln1f = (__u32) buflen;	/* length of message */
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipflags1 = (IPNORPY | IPBUFLST | flags1);
	b2f0_result = b2f0(SEND, parm);

	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");
	return b2f0_result;
}

/*
 * Name: iucv_send_prmmsg
 * Purpose: This function transmits data to another application.
 *          Prmmsg specifies that the 8-bytes of data are to be moved
 *          into the parameter list. This is a one-way message and the
 *          receiver will not reply to the message.
 * Input: pathid - path identification number
 *        trgcls - specifies target class
 *        srccls - specifies the source message class
 *        msgtag - specifies a tag to be associated with the message
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        prmmsg - 8-bytes of data to be placed into parameter list
 * Output: msgid - specifies the message ID.
 * Return: b2f0_result - return code from CP
*/
int
iucv_send_prmmsg (__u16 pathid,
		  __u32 * msgid,
		  __u32 trgcls,
		  __u32 srccls, __u32 msgtag, int flags1, __u8 prmmsg[8])
{
	iparml_dpl *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	parm = (iparml_dpl *)grab_param();

	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipflags1 = (IPRMDATA | IPNORPY | flags1);
	memcpy(parm->iprmmsg, prmmsg, sizeof(parm->iprmmsg));

	b2f0_result = b2f0(SEND, parm);

	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_send2way
 * Purpose: This function transmits data to another application.
 *          Data to be transmitted is in a buffer. The receiver
 *          of the send is expected to reply to the message and
 *          a buffer is provided into which IUCV moves the reply
 *          to this message.
 * Input: pathid - path identification number
 *        trgcls - specifies target class
 *        srccls - specifies the source message class
 *        msgtag - specifies a tag associated with the message
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        buffer - address of send buffer
 *        buflen - length of send buffer
 *        ansbuf - address of buffer to reply with
 *        anslen - length of buffer to reply with
 * Output: msgid - specifies the message ID.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - buffer or ansbuf address is NULL
 */
int
iucv_send2way (__u16 pathid,
	       __u32 * msgid,
	       __u32 trgcls,
	       __u32 srccls,
	       __u32 msgtag,
	       int flags1,
	       void *buffer, ulong buflen, void *ansbuf, ulong anslen)
{
	iparml_db *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!buffer || !ansbuf)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipbfadr1 = (__u32) ((ulong) buffer);
	parm->ipbfln1f = (__u32) buflen;	/* length of message */
	parm->ipbfadr2 = (__u32) ((ulong) ansbuf);
	parm->ipbfln2f = (__u32) anslen;
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipflags1 = flags1;	/* priority message */

	b2f0_result = b2f0(SEND, parm);

	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_send2way_array
 * Purpose: This function transmits data to another application.
 *          The contents of buffer is the address of the array of
 *          addresses and lengths of discontiguous buffers that hold
 *          the message text. The receiver of the send is expected to
 *          reply to the message and a buffer is provided into which
 *          IUCV moves the reply to this message.
 * Input: pathid - path identification number
 *        trgcls - specifies target class
 *        srccls - specifies the source message class
 *        msgtag - spcifies a tag to be associated with the message
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        buffer - address of array of send buffers
 *        buflen - total length of send buffers
 *        ansbuf - address of buffer to reply with
 *        anslen - length of buffer to reply with
 * Output: msgid - specifies the message ID.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - buffer address is NULL
 */
int
iucv_send2way_array (__u16 pathid,
		     __u32 * msgid,
		     __u32 trgcls,
		     __u32 srccls,
		     __u32 msgtag,
		     int flags1,
		     iucv_array_t * buffer,
		     ulong buflen, iucv_array_t * ansbuf, ulong anslen)
{
	iparml_db *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!buffer || !ansbuf)
		return -EINVAL;

	parm = (iparml_db *)grab_param();

	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipbfadr1 = (__u32) ((ulong) buffer);
	parm->ipbfln1f = (__u32) buflen;	/* length of message */
	parm->ipbfadr2 = (__u32) ((ulong) ansbuf);
	parm->ipbfln2f = (__u32) anslen;
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipflags1 = (IPBUFLST | IPANSLST | flags1);
	b2f0_result = b2f0(SEND, parm);
	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");
	return b2f0_result;
}

/*
 * Name: iucv_send2way_prmmsg
 * Purpose: This function transmits data to another application.
 *          Prmmsg specifies that the 8-bytes of data are to be moved
 *          into the parameter list. This is a two-way message and the
 *          receiver of the message is expected to reply. A buffer
 *          is provided into which IUCV moves the reply to this
 *          message.
 * Input: pathid - path identification number
 *        trgcls - specifies target class
 *        srccls - specifies the source message class
 *        msgtag - specifies a tag to be associated with the message
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        prmmsg - 8-bytes of data to be placed in parameter list
 *        ansbuf - address of buffer to reply with
 *        anslen - length of buffer to reply with
 * Output: msgid - specifies the message ID.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - buffer address is NULL
*/
int
iucv_send2way_prmmsg (__u16 pathid,
		      __u32 * msgid,
		      __u32 trgcls,
		      __u32 srccls,
		      __u32 msgtag,
		      ulong flags1, __u8 prmmsg[8], void *ansbuf, ulong anslen)
{
	iparml_dpl *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!ansbuf)
		return -EINVAL;

	parm = (iparml_dpl *)grab_param();

	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipbfadr2 = (__u32) ((ulong) ansbuf);
	parm->ipbfln2f = (__u32) anslen;
	parm->ipflags1 = (IPRMDATA | flags1);	/* message in prmlist */
	memcpy(parm->iprmmsg, prmmsg, sizeof(parm->iprmmsg));

	b2f0_result = b2f0(SEND, parm);

	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");

	return b2f0_result;
}

/*
 * Name: iucv_send2way_prmmsg_array
 * Purpose: This function transmits data to another application.
 *          Prmmsg specifies that the 8-bytes of data are to be moved
 *          into the parameter list. This is a two-way message and the
 *          receiver of the message is expected to reply. A buffer
 *          is provided into which IUCV moves the reply to this
 *          message. The contents of ansbuf is the address of the
 *          array of addresses and lengths of discontiguous buffers
 *          that contain the reply.
 * Input: pathid - path identification number
 *        trgcls - specifies target class
 *        srccls - specifies the source message class
 *        msgtag - specifies a tag to be associated with the message
 *        flags1 - option for path
 *                 IPPRTY- specifies if you want to send priority message
 *        prmmsg - 8-bytes of data to be placed into the parameter list
 *        ansbuf - address of buffer to reply with
 *        anslen - length of buffer to reply with
 * Output: msgid - specifies the message ID.
 * Return: b2f0_result - return code from CP
 *         (-EINVAL) - ansbuf address is NULL
 */
int
iucv_send2way_prmmsg_array (__u16 pathid,
			    __u32 * msgid,
			    __u32 trgcls,
			    __u32 srccls,
			    __u32 msgtag,
			    int flags1,
			    __u8 prmmsg[8],
			    iucv_array_t * ansbuf, ulong anslen)
{
	iparml_dpl *parm;
	ulong b2f0_result;

	iucv_debug(2, "entering");

	if (!ansbuf)
		return -EINVAL;

	parm = (iparml_dpl *)grab_param();

	parm->ippathid = pathid;
	parm->iptrgcls = trgcls;
	parm->ipsrccls = srccls;
	parm->ipmsgtag = msgtag;
	parm->ipbfadr2 = (__u32) ((ulong) ansbuf);
	parm->ipbfln2f = (__u32) anslen;
	parm->ipflags1 = (IPRMDATA | IPANSLST | flags1);
	memcpy(parm->iprmmsg, prmmsg, sizeof(parm->iprmmsg));
	b2f0_result = b2f0(SEND, parm);
	if ((!b2f0_result) && (msgid))
		*msgid = parm->ipmsgid;
	release_param(parm);

	iucv_debug(2, "exiting");
	return b2f0_result;
}

void
iucv_setmask_cpuid (void *result)
{
        iparml_set_mask *parm;

        iucv_debug(1, "entering");
        parm = (iparml_set_mask *)grab_param();
        parm->ipmask = *((__u8*)result);
        *((ulong *)result) = b2f0(SETMASK, parm);
        release_param(parm);

        iucv_debug(1, "b2f0_result = %ld", *((ulong *)result));
        iucv_debug(1, "exiting");
}

/*
 * Name: iucv_setmask
 * Purpose: This function enables or disables the following IUCV
 *          external interruptions: Nonpriority and priority message
 *          interrupts, nonpriority and priority reply interrupts.
 * Input: SetMaskFlag - options for interrupts
 *           0x80 - Nonpriority_MessagePendingInterruptsFlag
 *           0x40 - Priority_MessagePendingInterruptsFlag
 *           0x20 - Nonpriority_MessageCompletionInterruptsFlag
 *           0x10 - Priority_MessageCompletionInterruptsFlag
 *           0x08 - IUCVControlInterruptsFlag
 * Output: NA
 * Return: b2f0_result - return code from CP
*/
int
iucv_setmask (int SetMaskFlag)
{
	union {
		ulong result;
		__u8  param;
	} u;
	int cpu;

	u.param = SetMaskFlag;
	cpu = get_cpu();
	smp_call_function_on(iucv_setmask_cpuid, &u, 0, 1, iucv_cpuid);
	put_cpu();

	return u.result;
}

/**
 * iucv_sever:
 * @pathid:    Path identification number
 * @user_data: 16-byte of user data
 *
 * This function terminates an iucv path.
 * Returns: return code from CP
 */
int
iucv_sever(__u16 pathid, __u8 user_data[16])
{
	iparml_control *parm;
	ulong b2f0_result = 0;

	iucv_debug(1, "entering");
	parm = (iparml_control *)grab_param();

	memcpy(parm->ipuser, user_data, sizeof(parm->ipuser));
	parm->ippathid = pathid;

	b2f0_result = b2f0(SEVER, parm);

	if (!b2f0_result)
		iucv_remove_pathid(pathid);
	release_param(parm);

	iucv_debug(1, "exiting");
	return b2f0_result;
}

/*
 * Interrupt Handlers
 *******************************************************************************/

/**
 * iucv_irq_handler:
 * @regs: Current registers
 * @code: irq code
 *
 * Handles external interrupts coming in from CP.
 * Places the interrupt buffer on a queue and schedules iucv_tasklet_handler().
 */
static void
iucv_irq_handler(struct pt_regs *regs, __u16 code)
{
	iucv_irqdata *irqdata;

	irqdata = kmalloc(sizeof(iucv_irqdata), GFP_ATOMIC);
	if (!irqdata) {
		printk(KERN_WARNING "%s: out of memory\n", __FUNCTION__);
		return;
	}

	memcpy(&irqdata->data, iucv_external_int_buffer,
	       sizeof(iucv_GeneralInterrupt));

	spin_lock(&iucv_irq_queue_lock);
	list_add_tail(&irqdata->queue, &iucv_irq_queue);
	spin_unlock(&iucv_irq_queue_lock);

	tasklet_schedule(&iucv_tasklet);
}

/**
 * iucv_do_int:
 * @int_buf: Pointer to copy of external interrupt buffer
 *
 * The workhorse for handling interrupts queued by iucv_irq_handler().
 * This function is called from the bottom half iucv_tasklet_handler().
 */
static void
iucv_do_int(iucv_GeneralInterrupt * int_buf)
{
	handler *h = NULL;
	struct list_head *lh;
	ulong flags;
	iucv_interrupt_ops_t *interrupt = NULL;	/* interrupt addresses */
	__u8 temp_buff1[24], temp_buff2[24];	/* masked handler id. */
	int rc = 0, j = 0;
	__u8 no_listener[16] = "NO LISTENER";

	iucv_debug(2, "entering, pathid %d, type %02X",
		 int_buf->ippathid, int_buf->iptype);
	iucv_dumpit("External Interrupt Buffer:",
		    int_buf, sizeof(iucv_GeneralInterrupt));

	ASCEBC (no_listener, 16);

	if (int_buf->iptype != 01) {
		if ((int_buf->ippathid) > (max_connections - 1)) {
			printk(KERN_WARNING "%s: Got interrupt with pathid %d"
			       " > max_connections (%ld)\n", __FUNCTION__,
			       int_buf->ippathid, max_connections - 1);
		} else {
			h = iucv_pathid_table[int_buf->ippathid];
			interrupt = h->interrupt_table;
			iucv_dumpit("Handler:", h, sizeof(handler));
		}
	}

	/* end of if statement */
	switch (int_buf->iptype) {
		case 0x01:		/* connection pending */
			if (messagesDisabled) {
			    iucv_setmask(~0);
			    messagesDisabled = 0;
			}
			spin_lock_irqsave(&iucv_lock, flags);
			list_for_each(lh, &iucv_handler_table) {
				h = list_entry(lh, handler, list);
				memcpy(temp_buff1, &(int_buf->ipvmid), 24);
				memcpy(temp_buff2, &(h->id.userid), 24);
				for (j = 0; j < 24; j++) {
					temp_buff1[j] &= (h->id.mask)[j];
					temp_buff2[j] &= (h->id.mask)[j];
				}
				
				iucv_dumpit("temp_buff1:",
					    temp_buff1, sizeof(temp_buff1));
				iucv_dumpit("temp_buff2",
					    temp_buff2, sizeof(temp_buff2));
				
				if (!memcmp (temp_buff1, temp_buff2, 24)) {
					
					iucv_debug(2,
						   "found a matching handler");
					break;
				} else
					h = NULL;
			}
			spin_unlock_irqrestore (&iucv_lock, flags);
			if (h) {
				/* ADD PATH TO PATHID TABLE */
				rc = iucv_add_pathid(int_buf->ippathid, h);
				if (rc) {
					iucv_sever (int_buf->ippathid,
						    no_listener);
					iucv_debug(1,
						   "add_pathid failed, rc = %d",
						   rc);
				} else {
					interrupt = h->interrupt_table;
					if (interrupt->ConnectionPending) {
						EBCASC (int_buf->ipvmid, 8);
						interrupt->ConnectionPending(
							(iucv_ConnectionPending *)int_buf,
							h->pgm_data);
					} else
						iucv_sever(int_buf->ippathid,
							   no_listener);
				}
			} else
				iucv_sever(int_buf->ippathid, no_listener);
			break;
			
		case 0x02:		/*connection complete */
			if (messagesDisabled) {
			    iucv_setmask(~0);
			    messagesDisabled = 0;
			}
			if (h) {
				if (interrupt->ConnectionComplete)
				{
					interrupt->ConnectionComplete(
						(iucv_ConnectionComplete *)int_buf,
						h->pgm_data);
				}
				else
					iucv_debug(1,
						   "ConnectionComplete not called");
			} else
				iucv_sever(int_buf->ippathid, no_listener);
			break;
			
		case 0x03:		/* connection severed */
			if (messagesDisabled) {
			    iucv_setmask(~0);
			    messagesDisabled = 0;
			}
			if (h) {
				if (interrupt->ConnectionSevered)
					interrupt->ConnectionSevered(
						(iucv_ConnectionSevered *)int_buf,
						h->pgm_data);
				
				else
					iucv_sever (int_buf->ippathid, no_listener);
			} else
				iucv_sever(int_buf->ippathid, no_listener);
			break;
			
		case 0x04:		/* connection quiesced */
			if (messagesDisabled) {
			    iucv_setmask(~0);
			    messagesDisabled = 0;
			}
			if (h) {
				if (interrupt->ConnectionQuiesced)
					interrupt->ConnectionQuiesced(
						(iucv_ConnectionQuiesced *)int_buf,
						h->pgm_data);
				else
					iucv_debug(1,
						   "ConnectionQuiesced not called");
			}
			break;
			
		case 0x05:		/* connection resumed */
			if (messagesDisabled) {
			    iucv_setmask(~0);
			    messagesDisabled = 0;
			}
			if (h) {
				if (interrupt->ConnectionResumed)
					interrupt->ConnectionResumed(
						(iucv_ConnectionResumed *)int_buf,
						h->pgm_data);
				else
					iucv_debug(1,
						   "ConnectionResumed not called");
			}
			break;
			
		case 0x06:		/* priority message complete */
		case 0x07:		/* nonpriority message complete */
			if (h) {
				if (interrupt->MessageComplete)
					interrupt->MessageComplete(
						(iucv_MessageComplete *)int_buf,
						h->pgm_data);
				else
					iucv_debug(2,
						   "MessageComplete not called");
			}
			break;
			
		case 0x08:		/* priority message pending  */
		case 0x09:		/* nonpriority message pending  */
			if (h) {
				if (interrupt->MessagePending)
					interrupt->MessagePending(
						(iucv_MessagePending *) int_buf,
						h->pgm_data);
				else
					iucv_debug(2,
						   "MessagePending not called");
			}
			break;
		default:		/* unknown iucv type */
			printk(KERN_WARNING "%s: unknown iucv interrupt\n",
			       __FUNCTION__);
			break;
	}			/* end switch */
	
	iucv_debug(2, "exiting pathid %d, type %02X",
		 int_buf->ippathid, int_buf->iptype);

	return;
}

/**
 * iucv_tasklet_handler:
 *
 * This function loops over the queue of irq buffers and runs iucv_do_int()
 * on every queue element.
 */
static void
iucv_tasklet_handler(unsigned long ignored)
{
	struct list_head head;
	struct list_head *next;
	ulong  flags;

	spin_lock_irqsave(&iucv_irq_queue_lock, flags);
	list_add(&head, &iucv_irq_queue);
	list_del_init(&iucv_irq_queue);
	spin_unlock_irqrestore (&iucv_irq_queue_lock, flags);

	next = head.next;
	while (next != &head) {
		iucv_irqdata *p = list_entry(next, iucv_irqdata, queue);

		next = next->next;
		iucv_do_int(&p->data);
		kfree(p);
	}

	return;
}

subsys_initcall(iucv_init);
module_exit(iucv_exit);

/**
 * Export all public stuff
 */
EXPORT_SYMBOL (iucv_bus);
EXPORT_SYMBOL (iucv_root);
EXPORT_SYMBOL (iucv_accept);
EXPORT_SYMBOL (iucv_connect);
#if 0
EXPORT_SYMBOL (iucv_purge);
EXPORT_SYMBOL (iucv_query_maxconn);
EXPORT_SYMBOL (iucv_query_bufsize);
EXPORT_SYMBOL (iucv_quiesce);
#endif
EXPORT_SYMBOL (iucv_receive);
#if 0
EXPORT_SYMBOL (iucv_receive_array);
#endif
EXPORT_SYMBOL (iucv_reject);
#if 0
EXPORT_SYMBOL (iucv_reply);
EXPORT_SYMBOL (iucv_reply_array);
EXPORT_SYMBOL (iucv_resume);
#endif
EXPORT_SYMBOL (iucv_reply_prmmsg);
EXPORT_SYMBOL (iucv_send);
EXPORT_SYMBOL (iucv_send2way);
EXPORT_SYMBOL (iucv_send2way_array);
EXPORT_SYMBOL (iucv_send2way_prmmsg);
EXPORT_SYMBOL (iucv_send2way_prmmsg_array);
#if 0
EXPORT_SYMBOL (iucv_send_array);
EXPORT_SYMBOL (iucv_send_prmmsg);
EXPORT_SYMBOL (iucv_setmask);
#endif
EXPORT_SYMBOL (iucv_sever);
EXPORT_SYMBOL (iucv_register_program);
EXPORT_SYMBOL (iucv_unregister_program);
