6 İşlemeler 3b5e1e0b2f ... 2a524b0dcd

Yazar SHA1 Mesaj Tarih
  Tzafrir Cohen 2a524b0dcd Enable building zaphfc 13 yıl önce
  Tzafrir Cohen 058fdc9ba3 Typo (Stephan Eisvogel) 11 yıl önce
  Tzafrir Cohen 8d95a6098f zaphfc: fix the name of the license (lintian) 11 yıl önce
  Tzafrir Cohen 2f06f29621 zaphfc: indentation and such fixes 13 yıl önce
  Jaco Kroon 93429dd703 Fix index issue to allow zaphfc to get bri_ptmp into Up state. 13 yıl önce
  Tzafrir Cohen c0710a3fd1 Include ZapHFC 13 yıl önce

+ 1 - 0
drivers/dahdi/Kbuild

@@ -58,6 +58,7 @@ obj-$(DAHDI_BUILD_ALL)$(CONFIG_DAHDI_ECHOCAN_MG2)	+= dahdi_echocan_mg2.o
 
 ifdef CONFIG_PCI
 obj-$(DAHDI_BUILD_ALL)$(CONFIG_DAHDI_OPVXA1200)		+= opvxa1200/
+obj-$(DAHDI_BUILD_ALL)$(CONFIG_DAHDI_ZAPHFC)		+= zaphfc/
 endif
 
 obj-m += $(DAHDI_MODULES_EXTRA)

+ 13 - 0
drivers/dahdi/Kconfig

@@ -311,6 +311,19 @@ config DAHDI_OPVXA1200
 
 	  If unsure, say Y.
 
+config DAHDI_ZAPHFC
+	tristate "HFC-S DAHDI Driver"
+	depends on DAHDI && PCI
+	default DAHDI
+	---help---
+	  This driver provides DAHDI support for various HFC-S single-port
+          ISDN (BRI) cards.
+
+	  To compile this driver as a module, choose M here: the
+	  module will be called zaphfc.
+
+	  If unsure, say Y.
+
 config ECHO
 	tristate "Line Echo Canceller support"
 	default DAHDI

+ 10 - 0
drivers/dahdi/zaphfc/Kbuild

@@ -0,0 +1,10 @@
+obj-m += zaphfc.o
+
+EXTRA_CFLAGS := -I$(src)/.. -Wno-undef
+
+zaphfc-objs := base.o fifo.o
+
+$(obj)/base.o: $(src)/zaphfc.h
+$(obj)/fifo.o: $(src)/fifo.h
+
+

Dosya farkı çok büyük olduğundan ihmal edildi
+ 1720 - 0
drivers/dahdi/zaphfc/base.c


+ 375 - 0
drivers/dahdi/zaphfc/fifo.c

@@ -0,0 +1,375 @@
+/*
+ * fifo.c - HFC FIFO management routines
+ *
+ * Copyright (C) 2006 headissue GmbH; Jens Wilke
+ * Copyright (C) 2004 Daniele Orlandi
+ * Copyright (C) 2002, 2003, 2004, Junghanns.NET GmbH
+ *
+ * Original author of this code is
+ * Daniele "Vihai" Orlandi <daniele@orlandi.com>
+ *
+ * This program is free software and may be modified and
+ * distributed under the terms of the GNU General Public License.
+ *
+ */
+
+#include <linux/kernel.h>
+
+#include <dahdi/kernel.h>
+
+#include "fifo.h"
+
+static void hfc_fifo_mem_read(struct hfc_chan_simplex *chan,
+	int z_start,
+	void *data, int size)
+{
+	int bytes_to_boundary = chan->z_max - z_start + 1;
+	if (bytes_to_boundary >= size) {
+		memcpy(data,
+			chan->z_base + z_start,
+			size);
+	} else {
+		/*
+		 * Buffer wrap
+		 */
+		memcpy(data,
+			chan->z_base + z_start,
+			bytes_to_boundary);
+
+		memcpy(data + bytes_to_boundary,
+			chan->fifo_base,
+			size - bytes_to_boundary);
+	}
+}
+
+static void hfc_fifo_mem_write(struct hfc_chan_simplex *chan,
+	void *data, int size)
+{
+	int bytes_to_boundary = chan->z_max - *Z1_F1(chan) + 1;
+	if (bytes_to_boundary >= size) {
+		memcpy(chan->z_base + *Z1_F1(chan),
+			data,
+			size);
+	} else {
+		/*
+		 * FIFO wrap
+		 */
+
+		memcpy(chan->z_base + *Z1_F1(chan),
+			data,
+			bytes_to_boundary);
+
+		memcpy(chan->fifo_base,
+			data + bytes_to_boundary,
+			size - bytes_to_boundary);
+	}
+}
+
+int hfc_fifo_get(struct hfc_chan_simplex *chan,
+		void *data, int size)
+{
+	int available_bytes;
+
+	/*
+	 * Some useless statistic
+	 */
+	chan->bytes += size;
+
+	available_bytes = hfc_fifo_used_rx(chan);
+
+	if (available_bytes < size && !chan->fifo_underrun++) {
+		/*
+		 * print the warning only once
+		 */
+		printk(KERN_WARNING hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"RX FIFO not enough (%d) bytes to receive!\n",
+			chan->chan->card->cardnum,
+			chan->chan->name,
+			available_bytes);
+		return -1;
+	}
+
+	hfc_fifo_mem_read(chan, *Z2_F2(chan), data, size);
+	*Z2_F2(chan) = Z_inc(chan, *Z2_F2(chan), size);
+	return available_bytes - size;
+}
+
+void hfc_fifo_put(struct hfc_chan_simplex *chan,
+			void *data, int size)
+{
+	struct hfc_card *card = chan->chan->card;
+	int used_bytes = hfc_fifo_used_tx(chan);
+	int free_bytes = hfc_fifo_free_tx(chan);
+
+	if (!used_bytes && !chan->fifo_underrun++) {
+		/*
+		 * print warning only once, to make timing not worse
+		 */
+		printk(KERN_WARNING hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"TX FIFO has become empty\n",
+			card->cardnum,
+			chan->chan->name);
+	}
+	if (free_bytes < size) {
+		printk(KERN_CRIT hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"TX FIFO full!\n",
+			chan->chan->card->cardnum,
+			chan->chan->name);
+		chan->fifo_full++;
+		hfc_clear_fifo_tx(chan);
+	}
+
+	hfc_fifo_mem_write(chan, data, size);
+	chan->bytes += size;
+	*Z1_F1(chan) = Z_inc(chan, *Z1_F1(chan), size);
+}
+
+int hfc_fifo_get_frame(struct hfc_chan_simplex *chan, void *data, int max_size)
+{
+	int frame_size;
+	u16 newz2 ;
+
+	if (*chan->f1 == *chan->f2) {
+		/*
+		 * nothing received, strange uh?
+		 */
+		printk(KERN_WARNING hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"get_frame called with no frame in FIFO.\n",
+			chan->chan->card->cardnum,
+			chan->chan->name);
+
+		return -1;
+	}
+
+	/*
+	 * frame_size includes CRC+CRC+STAT
+	 */
+	frame_size = hfc_fifo_get_frame_size(chan);
+
+#ifdef DEBUG
+	if (debug_level == 3) {
+		printk(KERN_DEBUG hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"RX len %2d: ",
+			chan->chan->card->cardnum,
+			chan->chan->name,
+			frame_size);
+	} else if (debug_level >= 4) {
+		printk(KERN_DEBUG hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"RX (f1=%02x, f2=%02x, z1=%04x, z2=%04x) len %2d: ",
+			chan->chan->card->cardnum,
+			chan->chan->name,
+			*chan->f1, *chan->f2, *Z1_F2(chan), *Z2_F2(chan),
+			frame_size);
+	}
+
+	if (debug_level >= 3) {
+		int i;
+		for (i = 0; i < frame_size; i++) {
+			printk("%02x", hfc_fifo_u8(chan,
+				Z_inc(chan, *Z2_F2(chan), i)));
+		}
+
+		printk("\n");
+	}
+#endif
+
+	if (frame_size <= 0) {
+#ifdef DEBUG
+		if (debug_level >= 2) {
+			printk(KERN_DEBUG hfc_DRIVER_PREFIX
+				"card %d: "
+				"chan %s: "
+				"invalid (empty) frame received.\n",
+				chan->chan->card->cardnum,
+				chan->chan->name);
+		}
+#endif
+
+		hfc_fifo_drop_frame(chan);
+		return -1;
+	}
+
+	/*
+	 * STAT is not really received
+	 */
+	chan->bytes += frame_size - 1;
+
+	/*
+	 * Calculate beginning of the next frame
+	 */
+	newz2 = Z_inc(chan, *Z2_F2(chan), frame_size);
+
+	/*
+	 * We cannot use hfc_fifo_get because of different semantic of
+	 * "available bytes" and to avoid useless increment of Z2
+	 */
+	hfc_fifo_mem_read(chan, *Z2_F2(chan), data,
+		frame_size < max_size ? frame_size : max_size);
+
+	if (hfc_fifo_u8(chan, Z_inc(chan, *Z2_F2(chan),
+		frame_size - 1)) != 0x00) {
+		/*
+		 * CRC not ok, frame broken, skipping
+		 */
+#ifdef DEBUG
+		if (debug_level >= 2) {
+			printk(KERN_WARNING hfc_DRIVER_PREFIX
+				"card %d: "
+				"chan %s: "
+				"Received frame with wrong CRC\n",
+				chan->chan->card->cardnum,
+				chan->chan->name);
+		}
+#endif
+
+		chan->crc++;
+
+		hfc_fifo_drop_frame(chan);
+		return -1;
+	}
+
+	chan->frames++;
+
+	*chan->f2 = F_inc(chan, *chan->f2, 1);
+
+	/*
+	 * Set Z2 for the next frame we're going to receive
+	 */
+	*Z2_F2(chan) = newz2;
+
+	return frame_size;
+}
+
+void hfc_fifo_drop_frame(struct hfc_chan_simplex *chan)
+{
+	int available_bytes;
+	u16 newz2;
+
+	if (*chan->f1 == *chan->f2) {
+		/*
+		 * nothing received, strange eh?
+		 */
+		printk(KERN_WARNING hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"skip_frame called with no frame in FIFO.\n",
+			chan->chan->card->cardnum,
+			chan->chan->name);
+
+		return;
+	}
+
+	available_bytes = hfc_fifo_used_rx(chan) + 1;
+
+	/*
+	 * Calculate beginning of the next frame
+	 */
+	newz2 = Z_inc(chan, *Z2_F2(chan), available_bytes);
+
+	*chan->f2 = F_inc(chan, *chan->f2, 1);
+
+	/*
+	 * Set Z2 for the next frame we're going to receive
+	 */
+	*Z2_F2(chan) = newz2;
+}
+
+void hfc_fifo_put_frame(struct hfc_chan_simplex *chan,
+		 void *data, int size)
+{
+	u16 newz1;
+	int available_frames;
+
+#ifdef DEBUG
+	if (debug_level == 3) {
+		printk(KERN_DEBUG hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"TX len %2d: ",
+			chan->chan->card->cardnum,
+			chan->chan->name,
+			size);
+	} else if (debug_level >= 4) {
+		printk(KERN_DEBUG hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"TX (f1=%02x, f2=%02x, z1=%04x, z2=%04x) len %2d: ",
+			chan->chan->card->cardnum,
+			chan->chan->name,
+			*chan->f1, *chan->f2, *Z1_F1(chan), *Z2_F1(chan),
+			size);
+	}
+
+	if (debug_level >= 3) {
+		int i;
+		for (i = 0; i < size; i++)
+			printk("%02x", ((u8 *)data)[i]);
+
+		printk("\n");
+	}
+#endif
+
+	available_frames = hfc_fifo_free_frames(chan);
+
+	if (available_frames >= chan->f_num) {
+		printk(KERN_CRIT hfc_DRIVER_PREFIX
+			"card %d: "
+			"chan %s: "
+			"TX FIFO total number of frames exceeded!\n",
+			chan->chan->card->cardnum,
+			chan->chan->name);
+
+		chan->fifo_full++;
+
+		return;
+	}
+
+	hfc_fifo_put(chan, data, size);
+
+	newz1 = *Z1_F1(chan);
+
+	*chan->f1 = F_inc(chan, *chan->f1, 1);
+
+	*Z1_F1(chan) = newz1;
+
+	chan->frames++;
+}
+
+void hfc_clear_fifo_rx(struct hfc_chan_simplex *chan)
+{
+	*chan->f2 = *chan->f1;
+	*Z2_F2(chan) = *Z1_F2(chan);
+}
+
+void hfc_clear_fifo_tx(struct hfc_chan_simplex *chan)
+{
+	*chan->f1 = *chan->f2;
+	*Z1_F1(chan) = *Z2_F1(chan);
+
+	if (chan->chan->status == open_voice) {
+		/*
+		 * Make sure that at least hfc_TX_FIFO_PRELOAD bytes are
+		 * present in the TX FIFOs
+		 * Create hfc_TX_FIFO_PRELOAD bytes of empty data
+		 * (0x7f is mute audio)
+		 */
+		u8 empty_fifo[hfc_TX_FIFO_PRELOAD +
+			DAHDI_CHUNKSIZE + hfc_RX_FIFO_PRELOAD];
+		memset(empty_fifo, 0x7f, sizeof(empty_fifo));
+
+		hfc_fifo_put(chan, empty_fifo, sizeof(empty_fifo));
+	}
+}
+

+ 139 - 0
drivers/dahdi/zaphfc/fifo.h

@@ -0,0 +1,139 @@
+/*
+ * fifo.h - Dahdi driver for HFC-S PCI A based ISDN BRI cards
+ *
+ * Copyright (C) 2004 Daniele Orlandi
+ * Copyright (C) 2002, 2003, 2004, Junghanns.NET GmbH
+ *
+ * Daniele "Vihai" Orlandi <daniele@orlandi.com>
+ *
+ * Major rewrite of the driver made by
+ * Klaus-Peter Junghanns <kpj@junghanns.net>
+ *
+ * This program is free software and may be modified and
+ * distributed under the terms of the GNU General Public License.
+ *
+ */
+
+#ifndef _HFC_FIFO_H
+#define _HFC_FIFO_H
+
+#include "zaphfc.h"
+
+static inline u16 *Z1_F1(struct hfc_chan_simplex *chan)
+{
+	return chan->z1_base + (*chan->f1 * 4);
+}
+
+static inline u16 *Z2_F1(struct hfc_chan_simplex *chan)
+{
+	return chan->z2_base + (*chan->f1 * 4);
+}
+
+static inline u16 *Z1_F2(struct hfc_chan_simplex *chan)
+{
+	return chan->z1_base + (*chan->f2 * 4);
+}
+
+static inline u16 *Z2_F2(struct hfc_chan_simplex *chan)
+{
+	return chan->z2_base + (*chan->f2 * 4);
+}
+
+static inline u16 Z_inc(struct hfc_chan_simplex *chan, u16 z, u16 inc)
+{
+	/*
+	 * declared as u32 in order to manage overflows
+	 */
+	u32 newz = z + inc;
+	if (newz > chan->z_max)
+		newz -= chan->fifo_size;
+
+	return newz;
+}
+
+static inline u8 F_inc(struct hfc_chan_simplex *chan, u8 f, u8 inc)
+{
+	/*
+	 * declared as u16 in order to manage overflows
+	 */
+	u16 newf = f + inc;
+	if (newf > chan->f_max)
+		newf -= chan->f_num;
+
+	return newf;
+}
+
+static inline u16 hfc_fifo_used_rx(struct hfc_chan_simplex *chan)
+{
+	return (*Z1_F2(chan) - *Z2_F2(chan) +
+			chan->fifo_size) % chan->fifo_size;
+}
+
+static inline u16 hfc_fifo_get_frame_size(struct hfc_chan_simplex *chan)
+{
+ /*
+  * This +1 is needed because in frame mode the available bytes are Z2-Z1+1
+  * while in transparent mode I wouldn't consider the byte pointed by Z2 to
+  * be available, otherwise, the FIFO would always contain one byte, even
+  * when Z1==Z2
+  */
+
+	return hfc_fifo_used_rx(chan) + 1;
+}
+
+static inline u8 hfc_fifo_u8(struct hfc_chan_simplex *chan, u16 z)
+{
+	return *((u8 *)(chan->z_base + z));
+}
+
+static inline u16 hfc_fifo_used_tx(struct hfc_chan_simplex *chan)
+{
+	return (*Z1_F1(chan) - *Z2_F1(chan) +
+			chan->fifo_size) % chan->fifo_size;
+}
+
+static inline u16 hfc_fifo_free_rx(struct hfc_chan_simplex *chan)
+{
+	u16 free_bytes = *Z2_F1(chan) - *Z1_F1(chan);
+
+	if (free_bytes > 0)
+		return free_bytes;
+	else
+		return free_bytes + chan->fifo_size;
+}
+
+static inline u16 hfc_fifo_free_tx(struct hfc_chan_simplex *chan)
+{
+	u16 free_bytes = *Z2_F1(chan) - *Z1_F1(chan);
+
+	if (free_bytes > 0)
+		return free_bytes;
+	else
+		return free_bytes + chan->fifo_size;
+}
+
+static inline int hfc_fifo_has_frames(struct hfc_chan_simplex *chan)
+{
+	return *chan->f1 != *chan->f2;
+}
+
+static inline u8 hfc_fifo_used_frames(struct hfc_chan_simplex *chan)
+{
+	return (*chan->f1 - *chan->f2 + chan->f_num) % chan->f_num;
+}
+
+static inline u8 hfc_fifo_free_frames(struct hfc_chan_simplex *chan)
+{
+	return (*chan->f2 - *chan->f1 + chan->f_num) % chan->f_num;
+}
+
+int hfc_fifo_get(struct hfc_chan_simplex *chan, void *data, int size);
+void hfc_fifo_put(struct hfc_chan_simplex *chan, void *data, int size);
+void hfc_fifo_drop(struct hfc_chan_simplex *chan, int size);
+int hfc_fifo_get_frame(struct hfc_chan_simplex *chan, void *data, int max_size);
+void hfc_fifo_drop_frame(struct hfc_chan_simplex *chan);
+void hfc_fifo_put_frame(struct hfc_chan_simplex *chan, void *data, int size);
+void hfc_clear_fifo_rx(struct hfc_chan_simplex *chan);
+void hfc_clear_fifo_tx(struct hfc_chan_simplex *chan);
+
+#endif

+ 419 - 0
drivers/dahdi/zaphfc/zaphfc.h

@@ -0,0 +1,419 @@
+/*
+ * zaphfc.h - Dahdi driver for HFC-S PCI A based ISDN BRI cards
+ *
+ * Dahdi port by Jose A. Deniz <odicha@hotmail.com>
+ *
+ * Copyright (C) 2009 Jose A. Deniz
+ * Copyright (C) 2006 headissue GmbH; Jens Wilke
+ * Copyright (C) 2004 Daniele Orlandi
+ * Copyright (C) 2002, 2003, 2004, Junghanns.NET GmbH
+ *
+ * Jens Wilke <jw_vzaphfc@headissue.com>
+ *
+ * Orginal author of this code is
+ * Daniele "Vihai" Orlandi <daniele@orlandi.com>
+ *
+ * Major rewrite of the driver made by
+ * Klaus-Peter Junghanns <kpj@junghanns.net>
+ *
+ * This program is free software and may be modified and
+ * distributed under the terms of the GNU General Public License.
+ *
+ */
+
+#ifndef _HFC_ZAPHFC_H
+#define _HFC_ZAPHFC_H
+
+#include <asm/io.h>
+
+#define hfc_DRIVER_NAME "vzaphfc"
+#define hfc_DRIVER_PREFIX hfc_DRIVER_NAME ": "
+#define hfc_DRIVER_DESCR "HFC-S PCI A ISDN"
+#define hfc_DRIVER_VERSION "1.42"
+#define hfc_DRIVER_STRING hfc_DRIVER_DESCR " (V" hfc_DRIVER_VERSION ")"
+
+#define hfc_MAX_BOARDS 32
+
+#ifndef PCI_DMA_32BIT
+#define PCI_DMA_32BIT	0x00000000ffffffffULL
+#endif
+
+#ifndef PCI_VENDOR_ID_SITECOM
+#define PCI_VENDOR_ID_SITECOM 0x182D
+#endif
+
+#ifndef PCI_DEVICE_ID_SITECOM_3069
+#define PCI_DEVICE_ID_SITECOM_3069 0x3069
+#endif
+
+#define hfc_RESET_DELAY 20
+
+#define hfc_CLKDEL_TE	0x0f	/* CLKDEL in TE mode */
+#define hfc_CLKDEL_NT	0x6c	/* CLKDEL in NT mode */
+
+/* PCI memory mapped I/O */
+
+#define hfc_PCI_MEM_SIZE	0x0100
+#define hfc_PCI_MWBA		0x80
+
+/* GCI/IOM bus monitor registers */
+
+#define hfc_C_I       0x08
+#define hfc_TRxR      0x0C
+#define hfc_MON1_D    0x28
+#define hfc_MON2_D    0x2C
+
+
+/* GCI/IOM bus timeslot registers */
+
+#define hfc_B1_SSL    0x80
+#define hfc_B2_SSL    0x84
+#define hfc_AUX1_SSL  0x88
+#define hfc_AUX2_SSL  0x8C
+#define hfc_B1_RSL    0x90
+#define hfc_B2_RSL    0x94
+#define hfc_AUX1_RSL  0x98
+#define hfc_AUX2_RSL  0x9C
+
+/* GCI/IOM bus data registers */
+
+#define hfc_B1_D      0xA0
+#define hfc_B2_D      0xA4
+#define hfc_AUX1_D    0xA8
+#define hfc_AUX2_D    0xAC
+
+/* GCI/IOM bus configuration registers */
+
+#define hfc_MST_EMOD  0xB4
+#define hfc_MST_MODE	 0xB8
+#define hfc_CONNECT	 0xBC
+
+
+/* Interrupt and status registers */
+
+#define hfc_FIFO_EN   0x44
+#define hfc_TRM       0x48
+#define hfc_B_MODE    0x4C
+#define hfc_CHIP_ID   0x58
+#define hfc_CIRM	 0x60
+#define hfc_CTMT	 0x64
+#define hfc_INT_M1	 0x68
+#define hfc_INT_M2	 0x6C
+#define hfc_INT_S1	 0x78
+#define hfc_INT_S2	 0x7C
+#define hfc_STATUS	 0x70
+
+/* S/T section registers */
+
+#define hfc_STATES	 0xC0
+#define hfc_SCTRL	 0xC4
+#define hfc_SCTRL_E   0xC8
+#define hfc_SCTRL_R   0xCC
+#define hfc_SQ	 0xD0
+#define hfc_CLKDEL	 0xDC
+#define hfc_B1_REC    0xF0
+#define hfc_B1_SEND   0xF0
+#define hfc_B2_REC    0xF4
+#define hfc_B2_SEND   0xF4
+#define hfc_D_REC     0xF8
+#define hfc_D_SEND    0xF8
+#define hfc_E_REC     0xFC
+
+/* Bits and values in various HFC PCI registers */
+
+/* bits in status register (READ) */
+#define hfc_STATUS_PCI_PROC	0x02
+#define hfc_STATUS_NBUSY	0x04
+#define hfc_STATUS_TIMER_ELAP	0x10
+#define hfc_STATUS_STATINT	0x20
+#define hfc_STATUS_FRAMEINT	0x40
+#define hfc_STATUS_ANYINT	0x80
+
+/* bits in CTMT (Write) */
+#define hfc_CTMT_TRANSB1	0x01
+#define hfc_CTMT_TRANSB2	0x02
+#define hfc_CTMT_TIMER_CLEAR	0x80
+#define hfc_CTMT_TIMER_MASK	0x1C
+#define hfc_CTMT_TIMER_3_125	(0x01 << 2)
+#define hfc_CTMT_TIMER_6_25	(0x02 << 2)
+#define hfc_CTMT_TIMER_12_5	(0x03 << 2)
+#define hfc_CTMT_TIMER_25	(0x04 << 2)
+#define hfc_CTMT_TIMER_50	(0x05 << 2)
+#define hfc_CTMT_TIMER_400	(0x06 << 2)
+#define hfc_CTMT_TIMER_800	(0x07 << 2)
+#define hfc_CTMT_AUTO_TIMER	0x20
+
+/* bits in CIRM (Write) */
+#define hfc_CIRM_AUX_MSK	0x07
+#define hfc_CIRM_RESET		0x08
+#define hfc_CIRM_B1_REV		0x40
+#define hfc_CIRM_B2_REV		0x80
+
+/* bits in INT_M1 and INT_S1 */
+#define hfc_INTS_B1TRANS	0x01
+#define hfc_INTS_B2TRANS	0x02
+#define hfc_INTS_DTRANS		0x04
+#define hfc_INTS_B1REC		0x08
+#define hfc_INTS_B2REC		0x10
+#define hfc_INTS_DREC		0x20
+#define hfc_INTS_L1STATE	0x40
+#define hfc_INTS_TIMER		0x80
+
+/* bits in INT_M2 */
+#define hfc_M2_PROC_TRANS	0x01
+#define hfc_M2_GCI_I_CHG	0x02
+#define hfc_M2_GCI_MON_REC	0x04
+#define hfc_M2_IRQ_ENABLE	0x08
+#define hfc_M2_PMESEL		0x80
+
+/* bits in STATES */
+#define hfc_STATES_STATE_MASK	0x0F
+#define hfc_STATES_LOAD_STATE	0x10
+#define hfc_STATES_ACTIVATE	0x20
+#define hfc_STATES_DO_ACTION	0x40
+#define hfc_STATES_NT_G2_G3	0x80
+
+/* bits in HFCD_MST_MODE */
+#define hfc_MST_MODE_MASTER	0x01
+#define hfc_MST_MODE_SLAVE	0x00
+/* remaining bits are for codecs control */
+
+/* bits in HFCD_SCTRL */
+#define hfc_SCTRL_B1_ENA	0x01
+#define hfc_SCTRL_B2_ENA	0x02
+#define hfc_SCTRL_MODE_TE       0x00
+#define hfc_SCTRL_MODE_NT       0x04
+#define hfc_SCTRL_LOW_PRIO	0x08
+#define hfc_SCTRL_SQ_ENA	0x10
+#define hfc_SCTRL_TEST		0x20
+#define hfc_SCTRL_NONE_CAP	0x40
+#define hfc_SCTRL_PWR_DOWN	0x80
+
+/* bits in SCTRL_E  */
+#define hfc_SCTRL_E_AUTO_AWAKE	0x01
+#define hfc_SCTRL_E_DBIT_1	0x04
+#define hfc_SCTRL_E_IGNORE_COL	0x08
+#define hfc_SCTRL_E_CHG_B1_B2	0x80
+
+/* bits in SCTRL_R  */
+#define hfc_SCTRL_R_B1_ENA	0x01
+#define hfc_SCTRL_R_B2_ENA	0x02
+
+/* bits in FIFO_EN register */
+#define hfc_FIFOEN_B1TX		0x01
+#define hfc_FIFOEN_B1RX		0x02
+#define hfc_FIFOEN_B2TX		0x04
+#define hfc_FIFOEN_B2RX		0x08
+#define hfc_FIFOEN_DTX		0x10
+#define hfc_FIFOEN_DRX		0x20
+
+#define hfc_FIFOEN_B1		(hfc_FIFOEN_B1TX|hfc_FIFOEN_B1RX)
+#define hfc_FIFOEN_B2		(hfc_FIFOEN_B2TX|hfc_FIFOEN_B2RX)
+#define hfc_FIFOEN_D		(hfc_FIFOEN_DTX|hfc_FIFOEN_DRX)
+
+/* bits in the CONNECT register */
+#define	hfc_CONNECT_B1_HFC_from_ST		0x00
+#define	hfc_CONNECT_B1_HFC_from_GCI		0x01
+#define hfc_CONNECT_B1_ST_from_HFC		0x00
+#define hfc_CONNECT_B1_ST_from_GCI		0x02
+#define hfc_CONNECT_B1_GCI_from_HFC		0x00
+#define hfc_CONNECT_B1_GCI_from_ST		0x04
+
+#define	hfc_CONNECT_B2_HFC_from_ST		0x00
+#define	hfc_CONNECT_B2_HFC_from_GCI		0x08
+#define hfc_CONNECT_B2_ST_from_HFC		0x00
+#define hfc_CONNECT_B2_ST_from_GCI		0x10
+#define hfc_CONNECT_B2_GCI_from_HFC		0x00
+#define hfc_CONNECT_B2_GCI_from_ST		0x20
+
+/* bits in the TRM register */
+#define hfc_TRM_TRANS_INT_00	0x00
+#define hfc_TRM_TRANS_INT_01	0x01
+#define hfc_TRM_TRANS_INT_10	0x02
+#define hfc_TRM_TRANS_INT_11	0x04
+#define hfc_TRM_ECHO		0x20
+#define hfc_TRM_B1_PLUS_B2	0x40
+#define hfc_TRM_IOM_TEST_LOOP	0x80
+
+/* bits in the __SSL and __RSL registers */
+#define	hfc_SRSL_STIO		0x40
+#define hfc_SRSL_ENABLE		0x80
+#define hfc_SRCL_SLOT_MASK	0x1f
+
+/* FIFO memory definitions */
+
+#define hfc_FIFO_SIZE		0x8000
+
+#define hfc_UGLY_FRAMEBUF	0x2000
+
+#define hfc_TX_FIFO_PRELOAD	(DAHDI_CHUNKSIZE + 2)
+#define hfc_RX_FIFO_PRELOAD	4
+
+/* HDLC STUFF */
+#define hfc_HDLC_BUF_LEN	32
+/* arbitrary, just the max # of byts we will send to DAHDI per call */
+
+
+/* NOTE: FIFO pointers are not declared volatile because accesses to the
+ *       FIFOs are inherently safe.
+ */
+
+#ifdef DEBUG
+extern int debug_level;
+#endif
+
+struct hfc_chan;
+
+struct hfc_chan_simplex {
+	struct hfc_chan_duplex *chan;
+
+	u8 zaptel_buffer[DAHDI_CHUNKSIZE];
+
+	u8 ugly_framebuf[hfc_UGLY_FRAMEBUF];
+	int ugly_framebuf_size;
+	u16 ugly_framebuf_off;
+
+	void *z1_base, *z2_base;
+	void *fifo_base;
+	void *z_base;
+	u16 z_min;
+	u16 z_max;
+	u16 fifo_size;
+
+	u8 *f1, *f2;
+	u8 f_min;
+	u8 f_max;
+	u8 f_num;
+
+	unsigned long long frames;
+	unsigned long long bytes;
+	unsigned long long fifo_full;
+	unsigned long long crc;
+	unsigned long long fifo_underrun;
+};
+
+enum hfc_chan_status {
+	free,
+	open_framed,
+	open_voice,
+	sniff_aux,
+	loopback,
+};
+
+struct hfc_chan_duplex {
+	struct hfc_card *card;
+
+	char *name;
+	int number;
+
+	enum hfc_chan_status status;
+	int open_by_netdev;
+	int open_by_zaptel;
+
+	unsigned short protocol;
+
+	spinlock_t lock;
+
+	struct hfc_chan_simplex rx;
+	struct hfc_chan_simplex tx;
+
+};
+
+typedef struct hfc_card {
+	int cardnum;
+	struct pci_dev *pcidev;
+	struct dahdi_hfc *ztdev;
+	struct proc_dir_entry *proc_dir;
+	char proc_dir_name[32];
+
+	struct proc_dir_entry *proc_info;
+	struct proc_dir_entry *proc_fifos;
+	struct proc_dir_entry *proc_bufs;
+
+	unsigned long io_bus_mem;
+	void __iomem *io_mem;
+
+	dma_addr_t fifo_bus_mem;
+	void *fifo_mem;
+	void *fifos;
+
+	int nt_mode;
+	int sync_loss_reported;
+	int late_irqs;
+
+	u8 l1_state;
+	int fifo_suspended;
+	int ignore_first_timer_interrupt;
+
+	struct {
+		u8 m1;
+		u8 m2;
+		u8 fifo_en;
+		u8 trm;
+		u8 connect;
+		u8 sctrl;
+		u8 sctrl_r;
+		u8 sctrl_e;
+		u8 ctmt;
+		u8 cirm;
+	} regs;
+
+	struct hfc_chan_duplex chans[3];
+	int echo_enabled;
+
+
+
+	int debug_event;
+
+	spinlock_t lock;
+	unsigned int irq;
+	unsigned int iomem;
+	int ticks;
+	int clicks;
+	unsigned char *pci_io;
+	void *fifomem;		/* start of the shared mem */
+
+	unsigned int pcibus;
+	unsigned int pcidevfn;
+
+	int	drecinframe;
+
+	unsigned char cardno;
+	struct hfc_card *next;
+
+} hfc_card;
+
+typedef struct dahdi_hfc {
+	unsigned int usecount;
+	struct dahdi_device *ddev;
+	struct dahdi_span span;
+	struct dahdi_chan chans[3];
+	struct dahdi_chan *_chans[3];
+	struct hfc_card *card;
+
+	/* pointer to the signalling channel for this span */
+	struct dahdi_chan *sigchan;
+	/* nonzero means we're in the middle of sending an HDLC frame */
+	int sigactive;
+	/* hdlc_hard_xmit() increments, hdlc_tx_frame() decrements */
+	atomic_t hdlc_pending;
+	int frames_out;
+	int frames_in;
+} dahdi_hfc;
+
+static inline struct dahdi_hfc *dahdi_hfc_from_span(struct dahdi_span *span)
+{
+	return container_of(span, struct dahdi_hfc, span);
+}
+
+static inline u8 hfc_inb(struct hfc_card *card, int offset)
+{
+	return readb(card->io_mem + offset);
+}
+
+static inline void hfc_outb(struct hfc_card *card, int offset, u8 value)
+{
+	writeb(value, card->io_mem + offset);
+}
+
+#endif