diff --git a/drivers/dahdi/wcaxx-base.c b/drivers/dahdi/wcaxx-base.c index 504cccf..c17f1bc 100644 --- a/drivers/dahdi/wcaxx-base.c +++ b/drivers/dahdi/wcaxx-base.c @@ -3864,9 +3864,16 @@ static void wcaxx_back_out_gracefully(struct wcaxx *wc) kfree(wc); } +static void wcaxx_handle_error(struct wcxb *xb) +{ + struct wcaxx *wc = container_of(xb, struct wcaxx, xb); + wc->ddev->irqmisses++; +} + static const struct wcxb_operations wcxb_operations = { .handle_receive = wcaxx_handle_receive, .handle_transmit = wcaxx_handle_transmit, + .handle_error = wcaxx_handle_error, }; struct cmd_results { diff --git a/drivers/dahdi/wcte13xp-base.c b/drivers/dahdi/wcte13xp-base.c index 3ab89b1..726a63c 100644 --- a/drivers/dahdi/wcte13xp-base.c +++ b/drivers/dahdi/wcte13xp-base.c @@ -115,10 +115,17 @@ static void te13x_handle_transmit(struct wcxb *xb, void *vfp); static void te13x_handle_receive(struct wcxb *xb, void *vfp); static void te13x_handle_interrupt(struct wcxb *xb, u32 pending); +static void te13x_handle_error(struct wcxb *xb) +{ + struct t13x *wc = container_of(xb, struct t13x, xb); + wc->ddev->irqmisses++; +} + static struct wcxb_operations xb_ops = { .handle_receive = te13x_handle_receive, .handle_transmit = te13x_handle_transmit, .handle_interrupt = te13x_handle_interrupt, + .handle_error = te13x_handle_error, }; /* Maintenance Mode Registers */ diff --git a/drivers/dahdi/wcte43x-base.c b/drivers/dahdi/wcte43x-base.c index 056e113..af7b787 100644 --- a/drivers/dahdi/wcte43x-base.c +++ b/drivers/dahdi/wcte43x-base.c @@ -144,10 +144,17 @@ static void t43x_handle_transmit(struct wcxb *xb, void *vfp); static void t43x_handle_receive(struct wcxb *xb, void *vfp); static void t43x_handle_interrupt(struct wcxb *xb, u32 pending); +static void t43x_handle_error(struct wcxb *xb) +{ + struct t43x *wc = container_of(xb, struct t43x, xb); + wc->ddev->irqmisses++; +} + static struct wcxb_operations xb_ops = { .handle_receive = t43x_handle_receive, .handle_transmit = t43x_handle_transmit, .handle_interrupt = t43x_handle_interrupt, + .handle_error = t43x_handle_error, }; /* Maintenance Mode Registers */ diff --git a/drivers/dahdi/wcxb.c b/drivers/dahdi/wcxb.c index 191a0b0..5ae5325 100644 --- a/drivers/dahdi/wcxb.c +++ b/drivers/dahdi/wcxb.c @@ -397,6 +397,12 @@ static irqreturn_t _wcxb_isr(int irq, void *dev_id) if (pending & DESC_UNDERRUN) { u32 reg; + /* Report the error in case drivers have any custom + * methods for indicating potential data corruption. An + * underrun means data loss in the TDM channel. */ + if (xb->ops->handle_error) + xb->ops->handle_error(xb); + /* bump latency */ spin_lock(&xb->lock);