summaryrefslogtreecommitdiff
path: root/xpp/xpd.h
diff options
context:
space:
mode:
authorkpfleming <kpfleming@5390a7c7-147a-4af0-8ec9-7488f05a26cb>2006-02-15 02:26:14 +0000
committerkpfleming <kpfleming@5390a7c7-147a-4af0-8ec9-7488f05a26cb>2006-02-15 02:26:14 +0000
commita9ababa28c7ccedaf4be1501d009f99d9a7ba580 (patch)
treeb9259934f16b50693c73f9300287a7f92936837c /xpp/xpd.h
parent590e1c07e60d8564388533bb85deee9531df4893 (diff)
Merged revisions 949 via svnmerge from
https://origsvn.digium.com/svn/zaptel/branches/1.2 ........ r949 | kpfleming | 2006-02-14 20:24:18 -0600 (Tue, 14 Feb 2006) | 2 lines initial import of Xorcom Astribank driver (issue #6452, with minor mods) ........ git-svn-id: http://svn.digium.com/svn/zaptel/trunk@950 5390a7c7-147a-4af0-8ec9-7488f05a26cb
Diffstat (limited to 'xpp/xpd.h')
-rw-r--r--xpp/xpd.h290
1 files changed, 290 insertions, 0 deletions
diff --git a/xpp/xpd.h b/xpp/xpd.h
new file mode 100644
index 0000000..f563ca3
--- /dev/null
+++ b/xpp/xpd.h
@@ -0,0 +1,290 @@
+#ifndef XPD_H
+#define XPD_H
+
+/*
+ * Written by Oron Peled <oron@actcom.co.il>
+ * Copyright (C) 2004-2005, Xorcom
+ *
+ * All rights reserved.
+ *
+ * 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.
+ *
+ * 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.
+ *
+ */
+
+#include "xdefs.h"
+#include "xproto.h"
+
+#ifdef __KERNEL__
+#include <linux/kernel.h>
+#include <asm/atomic.h>
+#include <asm/semaphore.h>
+#include <linux/moduleparam.h>
+#endif
+
+#include <zaptel.h>
+
+#ifdef __KERNEL__
+#define DEF_PARM(type,name,init,desc) \
+ type name = init; \
+ module_param(name, type, 0600); \
+ MODULE_PARM_DESC(name, desc)
+
+#if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,12)
+/*
+ * Old 2.6 kernels had module_param_array() macro that receive the counter
+ * by value.
+ */
+#define DEF_ARRAY(type,name,count,init,desc) \
+ unsigned int name ## _num_values; \
+ type name[count] = {[0 ... count-1] = init}; \
+ module_param_array(name, type, name ## _num_values, 0600); \
+ MODULE_PARM_DESC(name, desc " ( 1-" __MODULE_STRING(count) ")")
+#else
+#define DEF_ARRAY(type,name,count,init,desc) \
+ unsigned int name ## _num_values; \
+ type name[count] = {[0 ... count-1] = init}; \
+ module_param_array(name, type, &name ## _num_values, 0600); \
+ MODULE_PARM_DESC(name, desc " ( 1-" __MODULE_STRING(count) ")")
+#endif
+#endif // __KERNEL__
+
+
+#define MAX_SPANNAME 20
+#define MAX_SPANDESC 40
+#define MAX_CHANNAME 20
+
+#define XPD_NAMELEN 10 /* must be <= from maximal workqueue name */
+#define XPD_DESCLEN 20
+#define XBUS_NAMELEN 20 /* must be <= from maximal workqueue name */
+#define XBUS_DESCLEN 40
+
+/* Hardware does not check bank_num yet. So only 4 cards can be used */
+#define MAX_XPDS 4 // 1 FXS + 2 E1/T1 + 1 (Quad * E1/T1)
+
+#define VALID_XPD_NUM(x) ((x) < MAX_XPDS && (x) >= 0)
+
+typedef struct xbus_ops xbus_ops_t;
+
+typedef enum xbus_type {
+ FIRMWARE_LOOPBACK = 1,
+ FIRMWARE_XPP = 2,
+} xbus_type_t;
+
+#ifdef __KERNEL__
+
+
+typedef struct packet_queue {
+ char qname[XPD_NAMELEN];
+ struct list_head head;
+ unsigned int count;
+ unsigned int worst_count;
+ unsigned int overflows;
+ spinlock_t lock;
+} packet_queue_t;
+
+struct xbus_ops {
+ int (*packet_send)(xbus_t *xbus, xpacket_t *packet);
+ xpacket_t *(*packet_new)(xbus_t *xbus, int flags);
+ void (*packet_free)(xbus_t *xbus, xpacket_t *p);
+};
+
+enum {
+ XBUS_N_DESC_REQ,
+ XBUS_N_DEV_DESC,
+ XBUS_N_PCM_WRITE,
+ XBUS_N_PCM_READ,
+ XBUS_N_TX_BYTES,
+ XBUS_N_RX_BYTES,
+ XBUS_N_SOFTSIM_PACKETS,
+ XBUS_N_SIM_PACKETS,
+};
+
+#define XBUS_COUNTER(xbus, counter) ((xbus)->counters[XBUS_N_ ## counter])
+
+#define C_(x) [ XBUS_N_ ## x ] = { #x }
+
+/* yucky, make an instance so we can size it... */
+static struct xbus_counters {
+ char *name;
+} xbus_counters[] = {
+ C_(DESC_REQ),
+ C_(DEV_DESC),
+ C_(PCM_WRITE),
+ C_(PCM_READ),
+ C_(TX_BYTES),
+ C_(RX_BYTES),
+ C_(SOFTSIM_PACKETS),
+ C_(SIM_PACKETS),
+};
+
+#undef C_
+
+#define XBUS_COUNTER_MAX ARRAY_SIZE(xbus_counters)
+
+struct xpd_sim {
+ bool simulated;
+ bool softloop_xpd;
+ int loopto;
+ xpd_type_t xpd_type;
+ xpp_line_t hookstate;
+};
+
+
+struct xbus {
+ char busname[XBUS_NAMELEN]; /* only xbus_new set this */
+ char busdesc[XBUS_DESCLEN]; /* lowlevel drivers set this */
+ int num;
+ xbus_ops_t *ops;
+ struct xpd *xpds[MAX_XPDS];
+
+ /* Simulator data */
+ xbus_type_t bus_type;
+#if SOFT_SIMULATOR
+ struct xpd_sim sim[MAX_XPDS];
+ struct workqueue_struct *sim_workqueue;
+ struct work_struct sim_work; // workqueue job for running simulator
+ packet_queue_t sim_packet_queue;
+#endif
+
+ spinlock_t lock;
+
+ bool hardware_exists; /* Hardware is functional */
+ int open_counter; /* Number of open channels */
+ atomic_t packet_counter; /* Allocated packets */
+ wait_queue_head_t packet_cache_empty;
+
+ struct timer_list poll_timer;
+ struct rw_semaphore in_use;
+ int num_xpds;
+ void *priv; /* Pointer to transport level data structures */
+
+#ifdef XPP_PACKET_LOG
+ struct cyclic_buff *packet_log;
+#endif
+
+#ifdef CONFIG_PROC_FS
+ struct proc_dir_entry *proc_xbus_dir;
+ struct proc_dir_entry *proc_xbus_summary;
+#endif
+
+ /* statistics */
+ int counters[XBUS_COUNTER_MAX];
+
+};
+#endif
+
+typedef enum xpd_direction {
+ TO_PHONE = 0,
+ TO_PSTN = 1,
+} xpd_direction_t;
+
+#define LINE_BITS (sizeof(xpp_line_t)*8)
+
+
+#ifdef __KERNEL__
+#define BIT_SET(x,i) ((x) |= (1 << (i)))
+#define BIT_CLR(x,i) ((x) &= ~(1 << (i)))
+#define IS_SET(x,i) (((x) & (1 << (i))) != 0)
+#define BIT(i) (1 << (i))
+
+enum {
+ XPD_N_PCM_READ,
+ XPD_N_PCM_WRITE,
+ XPD_N_RECV_ERRORS,
+};
+
+#define XPD_COUNTER(xpd, counter) ((xpd)->counters[XPD_N_ ## counter])
+
+#define C_(x) [ XPD_N_ ## x ] = { #x }
+
+/* yucky, make an instance so we can size it... */
+static struct xpd_counters {
+ char *name;
+} xpd_counters[] = {
+ C_(PCM_READ),
+ C_(PCM_WRITE),
+ C_(RECV_ERRORS),
+};
+
+#undef C_
+
+#define XPD_COUNTER_MAX (sizeof(xpd_counters)/sizeof(xpd_counters[0]))
+
+enum leds {
+ LED_GREEN,
+ LED_RED,
+ LED_BLUE,
+};
+
+#define NUM_LEDS 3
+
+struct xpd {
+ char xpdname[XPD_NAMELEN];
+ struct zt_span span;
+ struct zt_chan *chans;
+ int channels;
+ xpd_type_t type;
+ xpd_direction_t direction; /* TO_PHONE, TO_PSTN */
+ xpp_line_t enabled_chans; /* hardware activation: 0 - off, 1 - on */
+ xpp_line_t hookstate; /* 0 - ONHOOK, 1 - OFHOOK */
+ xpp_line_t ledstate[NUM_LEDS]; /* 0 - OFF, 1 - ON */
+ xpp_line_t digital_outputs; /* 0 - no, 1 - yes */
+ xpp_line_t digital_inputs; /* 0 - no, 1 - yes */
+
+ int ringing[CHANNELS_PERXPD];
+ bool ringer_on[CHANNELS_PERXPD]; /* For ring toggling */
+ bool led_on[CHANNELS_PERXPD]; /* For led toggling */
+ int lasttxhook[CHANNELS_PERXPD];
+
+ struct work_struct xpd_post_init;
+ xbus_t *xbus;
+
+ spinlock_t lock;
+ atomic_t open_counter; /* Number of open channels */
+
+ int flags;
+
+ unsigned int board_flags;
+#define XPD_BOARD_LOOPBACK 1
+
+#ifdef CONFIG_PROC_FS
+ struct proc_dir_entry *proc_xpd_dir;
+ struct proc_dir_entry *proc_xpd_summary;
+ struct proc_dir_entry *proc_xpd_ztregister;
+#endif
+ // Bit numbers of board_flags
+
+ int counters[XPD_COUNTER_MAX];
+
+ const xops_t *xops; /* Card level operations */
+ void *priv; /* Card level private data */
+ atomic_t card_present;
+
+ unsigned int recv_errors;
+ unsigned int seq_errors;
+ unsigned long last_response; /* in jiffies */
+ unsigned id;
+ struct list_head xpd_list;
+ unsigned int timer_count;
+ volatile u_char *writechunk; /* Double-word aligned write memory */
+ volatile u_char *readchunk; /* Double-word aligned read memory */
+ /* Echo cancelation */
+ u_char ec_chunk1[CHANNELS_PERXPD][ZT_CHUNKSIZE];
+ u_char ec_chunk2[CHANNELS_PERXPD][ZT_CHUNKSIZE];
+};
+
+#endif
+
+#endif /* XPD_H */