diff --git a/drivers/dahdi/wcaxx-base.c b/drivers/dahdi/wcaxx-base.c index b0fa8c6..86f979e 100644 --- a/drivers/dahdi/wcaxx-base.c +++ b/drivers/dahdi/wcaxx-base.c @@ -3872,9 +3872,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 cb16c63..2e5f1c9 100644 --- a/drivers/dahdi/wcte13xp-base.c +++ b/drivers/dahdi/wcte13xp-base.c @@ -118,10 +118,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 eab2afc..20476b8 100644 --- a/drivers/dahdi/wcte43x-base.c +++ b/drivers/dahdi/wcte43x-base.c @@ -147,10 +147,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);