From 2df9521deec68ee8b06fac1e1476f3433219ee73 Mon Sep 17 00:00:00 2001 From: Shaun Ruffell Date: Thu, 14 Apr 2011 20:32:29 +0000 Subject: wcte12xp: If we cannot read the mode selection pins fail the module load. Alexandre reported that on a particular server he would get a server crash when loading the wcte12xp driver after receiving a line about a timeout when trying to read the mode selection jumpers. If the driver times out when trying to read the mode selection bits there is a serious problem and it should not try to continue on with configuration / registration. Reported-and-Tested-by: Alexandre Abreu Signed-off-by: Shaun Ruffell Origin: http://svnview.digium.com/svn/dahdi?view=rev&rev=9902 git-svn-id: http://svn.asterisk.org/svn/dahdi/linux/branches/2.4@9904 a0bf4364-ded3-4de4-8d8a-66a801d63aff --- drivers/dahdi/wcte12xp/base.c | 35 +++++++++++++++++++++++++++-------- 1 file changed, 27 insertions(+), 8 deletions(-) diff --git a/drivers/dahdi/wcte12xp/base.c b/drivers/dahdi/wcte12xp/base.c index 156b603..bb88691 100644 --- a/drivers/dahdi/wcte12xp/base.c +++ b/drivers/dahdi/wcte12xp/base.c @@ -628,12 +628,22 @@ static void t1_setleds(struct t1 *wc, int leds) submit_cmd(wc, cmd); } -static inline int t1_getpins(struct t1 *wc, int inisr) +/** + * t1_getpins - Returns the value of the jumpers on the card. + * @wc: The card to read from. + * @pins: Pointer to u8 character to hold the pins value. + * + * Returns 0 on success, otherwise an error code. + * + */ +static int t1_getpins(struct t1 *wc, u8 *pins) { struct command *cmd; unsigned long flags; unsigned long ret; + *pins = 0; + cmd = get_free_cmd(wc); BUG_ON(!cmd); @@ -656,9 +666,9 @@ static inline int t1_getpins(struct t1 *wc, int inisr) } return ret; } - ret = cmd->data; + *pins = cmd->data; free_cmd(wc, cmd); - return ret; + return 0; } static void __t1xxp_set_clear(struct t1 *wc) @@ -1639,6 +1649,7 @@ static inline unsigned char t1_vpm_out(struct t1 *wc, int unit, const unsigned i static int t1_hardware_post_init(struct t1 *wc) { + int res; unsigned int reg; int x; @@ -1649,10 +1660,12 @@ static int t1_hardware_post_init(struct t1 *wc) else wc->spantype = TYPE_T1; } else { - if (t1_getpins(wc,0) & 0x01) /* returns 1 for T1 mode */ - wc->spantype = TYPE_T1; - else - wc->spantype = TYPE_E1; + u8 pins; + res = t1_getpins(wc, &pins); + if (res) + return res; + + wc->spantype = (pins & 0x01) ? TYPE_T1 : TYPE_E1; } debug_printk(wc, 1, "spantype: %s\n", 1 == wc->spantype ? "T1" : "E1"); @@ -2327,7 +2340,13 @@ static int __devinit te12xp_init_one(struct pci_dev *pdev, const struct pci_devi free_wc(wc); return -EIO; } - t1_hardware_post_init(wc); + + res = t1_hardware_post_init(wc); + if (res) { + voicebus_release(&wc->vb); + free_wc(wc); + return res; + } for (x = 0; x < (wc->spantype == TYPE_E1 ? 31 : 24); x++) { if (!(wc->chans[x] = kmalloc(sizeof(*wc->chans[x]), GFP_KERNEL))) { -- cgit v1.2.3