diff options
| author | Hansjoerg Lipp <hjlipp@web.de> | 2006-03-26 04:38:29 -0500 |
|---|---|---|
| committer | Linus Torvalds <torvalds@g5.osdl.org> | 2006-03-26 11:57:05 -0500 |
| commit | 6fd5ea63f85e30fda55b80939b4f379ea5db62b1 (patch) | |
| tree | e1f3d46ccb136535b0e7a6818b394c1d57173a24 | |
| parent | 0a34eb8f55a71678c379b47c25f562050c80efcc (diff) | |
[PATCH] isdn4linux: Siemens Gigaset drivers - common module
And: Tilman Schmidt <tilman@imap.cc>
This patch adds the common include file for the Siemens Gigaset drivers,
providing definitions used by all of the Gigaset ISDN driver source files. It
also adds the main source file of the gigaset module which manages common
functions not specific to the type of connection to the device.
Signed-off-by: Hansjoerg Lipp <hjlipp@web.de>
Signed-off-by: Tilman Schmidt <tilman@imap.cc>
Cc: Karsten Keil <kkeil@suse.de>
Cc: Greg KH <greg@kroah.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
| -rw-r--r-- | drivers/isdn/gigaset/common.c | 1203 | ||||
| -rw-r--r-- | drivers/isdn/gigaset/gigaset.h | 938 |
2 files changed, 2141 insertions, 0 deletions
diff --git a/drivers/isdn/gigaset/common.c b/drivers/isdn/gigaset/common.c new file mode 100644 index 000000000000..64371995c1a9 --- /dev/null +++ b/drivers/isdn/gigaset/common.c | |||
| @@ -0,0 +1,1203 @@ | |||
| 1 | /* | ||
| 2 | * Stuff used by all variants of the driver | ||
| 3 | * | ||
| 4 | * Copyright (c) 2001 by Stefan Eilers <Eilers.Stefan@epost.de>, | ||
| 5 | * Hansjoerg Lipp <hjlipp@web.de>, | ||
| 6 | * Tilman Schmidt <tilman@imap.cc>. | ||
| 7 | * | ||
| 8 | * ===================================================================== | ||
| 9 | * This program is free software; you can redistribute it and/or | ||
| 10 | * modify it under the terms of the GNU General Public License as | ||
| 11 | * published by the Free Software Foundation; either version 2 of | ||
| 12 | * the License, or (at your option) any later version. | ||
| 13 | * ===================================================================== | ||
| 14 | * ToDo: ... | ||
| 15 | * ===================================================================== | ||
| 16 | * Version: $Id: common.c,v 1.104.4.22 2006/02/04 18:28:16 hjlipp Exp $ | ||
| 17 | * ===================================================================== | ||
| 18 | */ | ||
| 19 | |||
| 20 | #include "gigaset.h" | ||
| 21 | #include <linux/ctype.h> | ||
| 22 | #include <linux/module.h> | ||
| 23 | #include <linux/moduleparam.h> | ||
| 24 | |||
| 25 | /* Version Information */ | ||
| 26 | #define DRIVER_AUTHOR "Hansjoerg Lipp <hjlipp@web.de>, Tilman Schmidt <tilman@imap.cc>, Stefan Eilers <Eilers.Stefan@epost.de>" | ||
| 27 | #define DRIVER_DESC "Driver for Gigaset 307x" | ||
| 28 | |||
| 29 | /* Module parameters */ | ||
| 30 | int gigaset_debuglevel = DEBUG_DEFAULT; | ||
| 31 | EXPORT_SYMBOL_GPL(gigaset_debuglevel); | ||
| 32 | module_param_named(debug, gigaset_debuglevel, int, S_IRUGO|S_IWUSR); | ||
| 33 | MODULE_PARM_DESC(debug, "debug level"); | ||
| 34 | |||
| 35 | /*====================================================================== | ||
| 36 | Prototypes of internal functions | ||
| 37 | */ | ||
| 38 | |||
| 39 | //static void gigaset_process_response(int resp_code, int parameter, | ||
| 40 | // struct at_state_t *at_state, | ||
| 41 | // unsigned char ** pstring); | ||
| 42 | static struct cardstate *alloc_cs(struct gigaset_driver *drv); | ||
| 43 | static void free_cs(struct cardstate *cs); | ||
| 44 | static void make_valid(struct cardstate *cs, unsigned mask); | ||
| 45 | static void make_invalid(struct cardstate *cs, unsigned mask); | ||
| 46 | |||
| 47 | #define VALID_MINOR 0x01 | ||
| 48 | #define VALID_ID 0x02 | ||
| 49 | #define ASSIGNED 0x04 | ||
| 50 | |||
| 51 | /* bitwise byte inversion table */ | ||
| 52 | __u8 gigaset_invtab[256] = { | ||
| 53 | 0x00, 0x80, 0x40, 0xc0, 0x20, 0xa0, 0x60, 0xe0, | ||
| 54 | 0x10, 0x90, 0x50, 0xd0, 0x30, 0xb0, 0x70, 0xf0, | ||
| 55 | 0x08, 0x88, 0x48, 0xc8, 0x28, 0xa8, 0x68, 0xe8, | ||
| 56 | 0x18, 0x98, 0x58, 0xd8, 0x38, 0xb8, 0x78, 0xf8, | ||
| 57 | 0x04, 0x84, 0x44, 0xc4, 0x24, 0xa4, 0x64, 0xe4, | ||
| 58 | 0x14, 0x94, 0x54, 0xd4, 0x34, 0xb4, 0x74, 0xf4, | ||
| 59 | 0x0c, 0x8c, 0x4c, 0xcc, 0x2c, 0xac, 0x6c, 0xec, | ||
| 60 | 0x1c, 0x9c, 0x5c, 0xdc, 0x3c, 0xbc, 0x7c, 0xfc, | ||
| 61 | 0x02, 0x82, 0x42, 0xc2, 0x22, 0xa2, 0x62, 0xe2, | ||
| 62 | 0x12, 0x92, 0x52, 0xd2, 0x32, 0xb2, 0x72, 0xf2, | ||
| 63 | 0x0a, 0x8a, 0x4a, 0xca, 0x2a, 0xaa, 0x6a, 0xea, | ||
| 64 | 0x1a, 0x9a, 0x5a, 0xda, 0x3a, 0xba, 0x7a, 0xfa, | ||
| 65 | 0x06, 0x86, 0x46, 0xc6, 0x26, 0xa6, 0x66, 0xe6, | ||
| 66 | 0x16, 0x96, 0x56, 0xd6, 0x36, 0xb6, 0x76, 0xf6, | ||
| 67 | 0x0e, 0x8e, 0x4e, 0xce, 0x2e, 0xae, 0x6e, 0xee, | ||
| 68 | 0x1e, 0x9e, 0x5e, 0xde, 0x3e, 0xbe, 0x7e, 0xfe, | ||
| 69 | 0x01, 0x81, 0x41, 0xc1, 0x21, 0xa1, 0x61, 0xe1, | ||
| 70 | 0x11, 0x91, 0x51, 0xd1, 0x31, 0xb1, 0x71, 0xf1, | ||
| 71 | 0x09, 0x89, 0x49, 0xc9, 0x29, 0xa9, 0x69, 0xe9, | ||
| 72 | 0x19, 0x99, 0x59, 0xd9, 0x39, 0xb9, 0x79, 0xf9, | ||
| 73 | 0x05, 0x85, 0x45, 0xc5, 0x25, 0xa5, 0x65, 0xe5, | ||
| 74 | 0x15, 0x95, 0x55, 0xd5, 0x35, 0xb5, 0x75, 0xf5, | ||
| 75 | 0x0d, 0x8d, 0x4d, 0xcd, 0x2d, 0xad, 0x6d, 0xed, | ||
| 76 | 0x1d, 0x9d, 0x5d, 0xdd, 0x3d, 0xbd, 0x7d, 0xfd, | ||
| 77 | 0x03, 0x83, 0x43, 0xc3, 0x23, 0xa3, 0x63, 0xe3, | ||
| 78 | 0x13, 0x93, 0x53, 0xd3, 0x33, 0xb3, 0x73, 0xf3, | ||
| 79 | 0x0b, 0x8b, 0x4b, 0xcb, 0x2b, 0xab, 0x6b, 0xeb, | ||
| 80 | 0x1b, 0x9b, 0x5b, 0xdb, 0x3b, 0xbb, 0x7b, 0xfb, | ||
| 81 | 0x07, 0x87, 0x47, 0xc7, 0x27, 0xa7, 0x67, 0xe7, | ||
| 82 | 0x17, 0x97, 0x57, 0xd7, 0x37, 0xb7, 0x77, 0xf7, | ||
| 83 | 0x0f, 0x8f, 0x4f, 0xcf, 0x2f, 0xaf, 0x6f, 0xef, | ||
| 84 | 0x1f, 0x9f, 0x5f, 0xdf, 0x3f, 0xbf, 0x7f, 0xff | ||
| 85 | }; | ||
| 86 | EXPORT_SYMBOL_GPL(gigaset_invtab); | ||
| 87 | |||
| 88 | void gigaset_dbg_buffer(enum debuglevel level, const unsigned char *msg, | ||
| 89 | size_t len, const unsigned char *buf, int from_user) | ||
| 90 | { | ||
| 91 | unsigned char outbuf[80]; | ||
| 92 | unsigned char inbuf[80 - 1]; | ||
| 93 | size_t numin; | ||
| 94 | const unsigned char *in; | ||
| 95 | size_t space = sizeof outbuf - 1; | ||
| 96 | unsigned char *out = outbuf; | ||
| 97 | |||
| 98 | if (!from_user) { | ||
| 99 | in = buf; | ||
| 100 | numin = len; | ||
| 101 | } else { | ||
| 102 | numin = len < sizeof inbuf ? len : sizeof inbuf; | ||
| 103 | in = inbuf; | ||
| 104 | if (copy_from_user(inbuf, (const unsigned char __user *) buf, numin)) { | ||
| 105 | strncpy(inbuf, "<FAULT>", sizeof inbuf); | ||
| 106 | numin = sizeof "<FAULT>" - 1; | ||
| 107 | } | ||
| 108 | } | ||
| 109 | |||
| 110 | for (; numin && space; --numin, ++in) { | ||
| 111 | --space; | ||
| 112 | if (*in >= 32) | ||
| 113 | *out++ = *in; | ||
| 114 | else { | ||
| 115 | *out++ = '^'; | ||
| 116 | if (space) { | ||
| 117 | *out++ = '@' + *in; | ||
| 118 | --space; | ||
| 119 | } | ||
| 120 | } | ||
| 121 | } | ||
| 122 | *out = 0; | ||
| 123 | |||
| 124 | dbg(level, "%s (%u bytes): %s", msg, (unsigned) len, outbuf); | ||
| 125 | } | ||
| 126 | EXPORT_SYMBOL_GPL(gigaset_dbg_buffer); | ||
| 127 | |||
| 128 | static int setflags(struct cardstate *cs, unsigned flags, unsigned delay) | ||
| 129 | { | ||
| 130 | int r; | ||
| 131 | |||
| 132 | r = cs->ops->set_modem_ctrl(cs, cs->control_state, flags); | ||
| 133 | cs->control_state = flags; | ||
| 134 | if (r < 0) | ||
| 135 | return r; | ||
| 136 | |||
| 137 | if (delay) { | ||
| 138 | set_current_state(TASK_INTERRUPTIBLE); | ||
| 139 | schedule_timeout(delay * HZ / 1000); | ||
| 140 | } | ||
| 141 | |||
| 142 | return 0; | ||
| 143 | } | ||
| 144 | |||
| 145 | int gigaset_enterconfigmode(struct cardstate *cs) | ||
| 146 | { | ||
| 147 | int i, r; | ||
| 148 | |||
| 149 | if (!atomic_read(&cs->connected)) { | ||
| 150 | err("not connected!"); | ||
| 151 | return -1; | ||
| 152 | } | ||
| 153 | |||
| 154 | cs->control_state = TIOCM_RTS; //FIXME | ||
| 155 | |||
| 156 | r = setflags(cs, TIOCM_DTR, 200); | ||
| 157 | if (r < 0) | ||
| 158 | goto error; | ||
| 159 | r = setflags(cs, 0, 200); | ||
| 160 | if (r < 0) | ||
| 161 | goto error; | ||
| 162 | for (i = 0; i < 5; ++i) { | ||
| 163 | r = setflags(cs, TIOCM_RTS, 100); | ||
| 164 | if (r < 0) | ||
| 165 | goto error; | ||
| 166 | r = setflags(cs, 0, 100); | ||
| 167 | if (r < 0) | ||
| 168 | goto error; | ||
| 169 | } | ||
| 170 | r = setflags(cs, TIOCM_RTS|TIOCM_DTR, 800); | ||
| 171 | if (r < 0) | ||
| 172 | goto error; | ||
| 173 | |||
| 174 | return 0; | ||
| 175 | |||
| 176 | error: | ||
| 177 | err("error %d on setuartbits!\n", -r); | ||
| 178 | cs->control_state = TIOCM_RTS|TIOCM_DTR; // FIXME is this a good value? | ||
| 179 | cs->ops->set_modem_ctrl(cs, 0, TIOCM_RTS|TIOCM_DTR); | ||
| 180 | |||
| 181 | return -1; //r | ||
| 182 | } | ||
| 183 | |||
| 184 | static int test_timeout(struct at_state_t *at_state) | ||
| 185 | { | ||
| 186 | if (!at_state->timer_expires) | ||
| 187 | return 0; | ||
| 188 | |||
| 189 | if (--at_state->timer_expires) { | ||
| 190 | dbg(DEBUG_MCMD, "decreased timer of %p to %lu", | ||
| 191 | at_state, at_state->timer_expires); | ||
