Commit c626c127 authored by Karsten Keil's avatar Karsten Keil Committed by David S. Miller

mISDN: Make layer1 timer 3 value configurable

For certification test it is very useful to change the layer1
timer3 value on runtime.
Signed-off-by: default avatarKarsten Keil <kkeil@linux-pingi.de>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 8423e6b2
...@@ -868,7 +868,7 @@ channel_ctrl(struct fritzcard *fc, struct mISDN_ctrl_req *cq) ...@@ -868,7 +868,7 @@ channel_ctrl(struct fritzcard *fc, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = MISDN_CTRL_LOOP; cq->op = MISDN_CTRL_LOOP | MISDN_CTRL_L1_TIMER3;
break; break;
case MISDN_CTRL_LOOP: case MISDN_CTRL_LOOP:
/* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */ /* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */
...@@ -878,6 +878,9 @@ channel_ctrl(struct fritzcard *fc, struct mISDN_ctrl_req *cq) ...@@ -878,6 +878,9 @@ channel_ctrl(struct fritzcard *fc, struct mISDN_ctrl_req *cq)
} }
ret = fc->isac.ctrl(&fc->isac, HW_TESTLOOP, cq->channel); ret = fc->isac.ctrl(&fc->isac, HW_TESTLOOP, cq->channel);
break; break;
case MISDN_CTRL_L1_TIMER3:
ret = fc->isac.ctrl(&fc->isac, HW_TIMER3_VALUE, cq->p1);
break;
default: default:
pr_info("%s: %s unknown Op %x\n", fc->name, __func__, cq->op); pr_info("%s: %s unknown Op %x\n", fc->name, __func__, cq->op);
ret = -EINVAL; ret = -EINVAL;
......
...@@ -4161,7 +4161,7 @@ channel_dctrl(struct dchannel *dch, struct mISDN_ctrl_req *cq) ...@@ -4161,7 +4161,7 @@ channel_dctrl(struct dchannel *dch, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = MISDN_CTRL_HFC_OP; cq->op = MISDN_CTRL_HFC_OP | MISDN_CTRL_L1_TIMER3;
break; break;
case MISDN_CTRL_HFC_WD_INIT: /* init the watchdog */ case MISDN_CTRL_HFC_WD_INIT: /* init the watchdog */
wd_cnt = cq->p1 & 0xf; wd_cnt = cq->p1 & 0xf;
...@@ -4191,6 +4191,9 @@ channel_dctrl(struct dchannel *dch, struct mISDN_ctrl_req *cq) ...@@ -4191,6 +4191,9 @@ channel_dctrl(struct dchannel *dch, struct mISDN_ctrl_req *cq)
__func__); __func__);
HFC_outb(hc, R_BERT_WD_MD, hc->hw.r_bert_wd_md | V_WD_RES); HFC_outb(hc, R_BERT_WD_MD, hc->hw.r_bert_wd_md | V_WD_RES);
break; break;
case MISDN_CTRL_L1_TIMER3:
ret = l1_event(dch->l1, HW_TIMER3_VALUE | (cq->p1 & 0xff));
break;
default: default:
printk(KERN_WARNING "%s: unknown Op %x\n", printk(KERN_WARNING "%s: unknown Op %x\n",
__func__, cq->op); __func__, cq->op);
......
...@@ -1819,7 +1819,7 @@ channel_ctrl(struct hfc_pci *hc, struct mISDN_ctrl_req *cq) ...@@ -1819,7 +1819,7 @@ channel_ctrl(struct hfc_pci *hc, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = MISDN_CTRL_LOOP | MISDN_CTRL_CONNECT | cq->op = MISDN_CTRL_LOOP | MISDN_CTRL_CONNECT |
MISDN_CTRL_DISCONNECT; MISDN_CTRL_DISCONNECT | MISDN_CTRL_L1_TIMER3;
break; break;
case MISDN_CTRL_LOOP: case MISDN_CTRL_LOOP:
/* channel 0 disabled loop */ /* channel 0 disabled loop */
...@@ -1896,6 +1896,9 @@ channel_ctrl(struct hfc_pci *hc, struct mISDN_ctrl_req *cq) ...@@ -1896,6 +1896,9 @@ channel_ctrl(struct hfc_pci *hc, struct mISDN_ctrl_req *cq)
Write_hfc(hc, HFCPCI_CONNECT, hc->hw.conn); Write_hfc(hc, HFCPCI_CONNECT, hc->hw.conn);
hc->hw.trm &= 0x7f; /* disable IOM-loop */ hc->hw.trm &= 0x7f; /* disable IOM-loop */
break; break;
case MISDN_CTRL_L1_TIMER3:
ret = l1_event(hc->dch.l1, HW_TIMER3_VALUE | (cq->p1 & 0xff));
break;
default: default:
printk(KERN_WARNING "%s: unknown Op %x\n", printk(KERN_WARNING "%s: unknown Op %x\n",
__func__, cq->op); __func__, cq->op);
......
...@@ -603,10 +603,11 @@ isac_l1hw(struct mISDNchannel *ch, struct sk_buff *skb) ...@@ -603,10 +603,11 @@ isac_l1hw(struct mISDNchannel *ch, struct sk_buff *skb)
} }
static int static int
isac_ctrl(struct isac_hw *isac, u32 cmd, u_long para) isac_ctrl(struct isac_hw *isac, u32 cmd, unsigned long para)
{ {
u8 tl = 0; u8 tl = 0;
u_long flags; unsigned long flags;
int ret = 0;
switch (cmd) { switch (cmd) {
case HW_TESTLOOP: case HW_TESTLOOP:
...@@ -626,12 +627,15 @@ isac_ctrl(struct isac_hw *isac, u32 cmd, u_long para) ...@@ -626,12 +627,15 @@ isac_ctrl(struct isac_hw *isac, u32 cmd, u_long para)
} }
spin_unlock_irqrestore(isac->hwlock, flags); spin_unlock_irqrestore(isac->hwlock, flags);
break; break;
case HW_TIMER3_VALUE:
ret = l1_event(isac->dch.l1, HW_TIMER3_VALUE | (para & 0xff));
break;
default: default:
pr_debug("%s: %s unknown command %x %lx\n", isac->name, pr_debug("%s: %s unknown command %x %lx\n", isac->name,
__func__, cmd, para); __func__, cmd, para);
return -1; ret = -1;
} }
return 0; return ret;
} }
static int static int
...@@ -1526,7 +1530,7 @@ channel_ctrl(struct ipac_hw *ipac, struct mISDN_ctrl_req *cq) ...@@ -1526,7 +1530,7 @@ channel_ctrl(struct ipac_hw *ipac, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = MISDN_CTRL_LOOP; cq->op = MISDN_CTRL_LOOP | MISDN_CTRL_L1_TIMER3;
break; break;
case MISDN_CTRL_LOOP: case MISDN_CTRL_LOOP:
/* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */ /* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */
...@@ -1536,6 +1540,9 @@ channel_ctrl(struct ipac_hw *ipac, struct mISDN_ctrl_req *cq) ...@@ -1536,6 +1540,9 @@ channel_ctrl(struct ipac_hw *ipac, struct mISDN_ctrl_req *cq)
} }
ret = ipac->ctrl(ipac, HW_TESTLOOP, cq->channel); ret = ipac->ctrl(ipac, HW_TESTLOOP, cq->channel);
break; break;
case MISDN_CTRL_L1_TIMER3:
ret = ipac->isac.ctrl(&ipac->isac, HW_TIMER3_VALUE, cq->p1);
break;
default: default:
pr_info("%s: unknown CTRL OP %x\n", ipac->name, cq->op); pr_info("%s: unknown CTRL OP %x\n", ipac->name, cq->op);
ret = -EINVAL; ret = -EINVAL;
......
...@@ -837,7 +837,7 @@ channel_ctrl(struct tiger_hw *card, struct mISDN_ctrl_req *cq) ...@@ -837,7 +837,7 @@ channel_ctrl(struct tiger_hw *card, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = MISDN_CTRL_LOOP; cq->op = MISDN_CTRL_LOOP | MISDN_CTRL_L1_TIMER3;
break; break;
case MISDN_CTRL_LOOP: case MISDN_CTRL_LOOP:
/* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */ /* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */
...@@ -847,6 +847,9 @@ channel_ctrl(struct tiger_hw *card, struct mISDN_ctrl_req *cq) ...@@ -847,6 +847,9 @@ channel_ctrl(struct tiger_hw *card, struct mISDN_ctrl_req *cq)
} }
ret = card->isac.ctrl(&card->isac, HW_TESTLOOP, cq->channel); ret = card->isac.ctrl(&card->isac, HW_TESTLOOP, cq->channel);
break; break;
case MISDN_CTRL_L1_TIMER3:
ret = card->isac.ctrl(&card->isac, HW_TIMER3_VALUE, cq->p1);
break;
default: default:
pr_info("%s: %s unknown Op %x\n", card->name, __func__, cq->op); pr_info("%s: %s unknown Op %x\n", card->name, __func__, cq->op);
ret = -EINVAL; ret = -EINVAL;
......
...@@ -224,7 +224,7 @@ channel_ctrl(struct sfax_hw *sf, struct mISDN_ctrl_req *cq) ...@@ -224,7 +224,7 @@ channel_ctrl(struct sfax_hw *sf, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = MISDN_CTRL_LOOP; cq->op = MISDN_CTRL_LOOP | MISDN_CTRL_L1_TIMER3;
break; break;
case MISDN_CTRL_LOOP: case MISDN_CTRL_LOOP:
/* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */ /* cq->channel: 0 disable, 1 B1 loop 2 B2 loop, 3 both */
...@@ -234,6 +234,9 @@ channel_ctrl(struct sfax_hw *sf, struct mISDN_ctrl_req *cq) ...@@ -234,6 +234,9 @@ channel_ctrl(struct sfax_hw *sf, struct mISDN_ctrl_req *cq)
} }
ret = sf->isac.ctrl(&sf->isac, HW_TESTLOOP, cq->channel); ret = sf->isac.ctrl(&sf->isac, HW_TESTLOOP, cq->channel);
break; break;
case MISDN_CTRL_L1_TIMER3:
ret = sf->isac.ctrl(&sf->isac, HW_TIMER3_VALUE, cq->p1);
break;
default: default:
pr_info("%s: unknown Op %x\n", sf->name, cq->op); pr_info("%s: unknown Op %x\n", sf->name, cq->op);
ret = -EINVAL; ret = -EINVAL;
......
...@@ -1035,7 +1035,10 @@ channel_ctrl(struct w6692_hw *card, struct mISDN_ctrl_req *cq) ...@@ -1035,7 +1035,10 @@ channel_ctrl(struct w6692_hw *card, struct mISDN_ctrl_req *cq)
switch (cq->op) { switch (cq->op) {
case MISDN_CTRL_GETOP: case MISDN_CTRL_GETOP:
cq->op = 0; cq->op = MISDN_CTRL_L1_TIMER3;
break;
case MISDN_CTRL_L1_TIMER3:
ret = l1_event(card->dch.l1, HW_TIMER3_VALUE | (cq->p1 & 0xff));
break; break;
default: default:
pr_info("%s: unknown CTRL OP %x\n", card->name, cq->op); pr_info("%s: unknown CTRL OP %x\n", card->name, cq->op);
......
...@@ -30,11 +30,12 @@ struct layer1 { ...@@ -30,11 +30,12 @@ struct layer1 {
struct FsmInst l1m; struct FsmInst l1m;
struct FsmTimer timer; struct FsmTimer timer;
int delay; int delay;
int t3_value;
struct dchannel *dch; struct dchannel *dch;
dchannel_l1callback *dcb; dchannel_l1callback *dcb;
}; };
#define TIMER3_VALUE 7000 #define TIMER3_DEFAULT_VALUE 7000
static static
struct Fsm l1fsm_s = {NULL, 0, 0, NULL, NULL}; struct Fsm l1fsm_s = {NULL, 0, 0, NULL, NULL};
...@@ -233,7 +234,7 @@ l1_activate_s(struct FsmInst *fi, int event, void *arg) ...@@ -233,7 +234,7 @@ l1_activate_s(struct FsmInst *fi, int event, void *arg)
{ {
struct layer1 *l1 = fi->userdata; struct layer1 *l1 = fi->userdata;
mISDN_FsmRestartTimer(&l1->timer, TIMER3_VALUE, EV_TIMER3, NULL, 2); mISDN_FsmRestartTimer(&l1->timer, l1->t3_value, EV_TIMER3, NULL, 2);
test_and_set_bit(FLG_L1_T3RUN, &l1->Flags); test_and_set_bit(FLG_L1_T3RUN, &l1->Flags);
l1->dcb(l1->dch, HW_RESET_REQ); l1->dcb(l1->dch, HW_RESET_REQ);
} }
...@@ -356,6 +357,16 @@ l1_event(struct layer1 *l1, u_int event) ...@@ -356,6 +357,16 @@ l1_event(struct layer1 *l1, u_int event)
release_l1(l1); release_l1(l1);
break; break;
default: default:
if ((event & ~HW_TIMER3_VMASK) == HW_TIMER3_VALUE) {
int val = event & HW_TIMER3_VMASK;
if (val < 5)
val = 5;
if (val > 30)
val = 30;
l1->t3_value = val;
break;
}
if (*debug & DEBUG_L1) if (*debug & DEBUG_L1)
printk(KERN_DEBUG "%s %x unhandled\n", printk(KERN_DEBUG "%s %x unhandled\n",
__func__, event); __func__, event);
...@@ -377,6 +388,7 @@ create_l1(struct dchannel *dch, dchannel_l1callback *dcb) { ...@@ -377,6 +388,7 @@ create_l1(struct dchannel *dch, dchannel_l1callback *dcb) {
nl1->l1m.fsm = &l1fsm_s; nl1->l1m.fsm = &l1fsm_s;
nl1->l1m.state = ST_L1_F3; nl1->l1m.state = ST_L1_F3;
nl1->Flags = 0; nl1->Flags = 0;
nl1->t3_value = TIMER3_DEFAULT_VALUE;
nl1->l1m.debug = *debug & DEBUG_L1_FSM; nl1->l1m.debug = *debug & DEBUG_L1_FSM;
nl1->l1m.userdata = nl1; nl1->l1m.userdata = nl1;
nl1->l1m.userint = 0; nl1->l1m.userint = 0;
......
...@@ -135,6 +135,9 @@ extern int create_l1(struct dchannel *, dchannel_l1callback *); ...@@ -135,6 +135,9 @@ extern int create_l1(struct dchannel *, dchannel_l1callback *);
#define HW_TESTRX_RAW 0x9602 #define HW_TESTRX_RAW 0x9602
#define HW_TESTRX_HDLC 0x9702 #define HW_TESTRX_HDLC 0x9702
#define HW_TESTRX_OFF 0x9802 #define HW_TESTRX_OFF 0x9802
#define HW_TIMER3_IND 0x9902
#define HW_TIMER3_VALUE 0x9a00
#define HW_TIMER3_VMASK 0x00FF
struct layer1; struct layer1;
extern int l1_event(struct layer1 *, u_int); extern int l1_event(struct layer1 *, u_int);
......
...@@ -37,7 +37,7 @@ ...@@ -37,7 +37,7 @@
*/ */
#define MISDN_MAJOR_VERSION 1 #define MISDN_MAJOR_VERSION 1
#define MISDN_MINOR_VERSION 1 #define MISDN_MINOR_VERSION 1
#define MISDN_RELEASE 26 #define MISDN_RELEASE 27
/* primitives for information exchange /* primitives for information exchange
* generell format * generell format
...@@ -372,6 +372,7 @@ clear_channelmap(u_int nr, u_char *map) ...@@ -372,6 +372,7 @@ clear_channelmap(u_int nr, u_char *map)
#define MISDN_CTRL_RX_OFF 0x0100 #define MISDN_CTRL_RX_OFF 0x0100
#define MISDN_CTRL_FILL_EMPTY 0x0200 #define MISDN_CTRL_FILL_EMPTY 0x0200
#define MISDN_CTRL_GETPEER 0x0400 #define MISDN_CTRL_GETPEER 0x0400
#define MISDN_CTRL_L1_TIMER3 0x0800
#define MISDN_CTRL_HW_FEATURES_OP 0x2000 #define MISDN_CTRL_HW_FEATURES_OP 0x2000
#define MISDN_CTRL_HW_FEATURES 0x2001 #define MISDN_CTRL_HW_FEATURES 0x2001
#define MISDN_CTRL_HFC_OP 0x4000 #define MISDN_CTRL_HFC_OP 0x4000
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment