summaryrefslogtreecommitdiff
path: root/drivers/dahdi/dahdi_dynamic_loc.c
diff options
context:
space:
mode:
authorShaun Ruffell <sruffell@digium.com>2011-01-03 18:24:52 +0000
committerShaun Ruffell <sruffell@digium.com>2011-01-03 18:24:52 +0000
commitee7da50e70c68b3497cfa193c0c826c2cf397dfb (patch)
treefc36cd8dbd2cd0937ec1978d4b328e112fc4e988 /drivers/dahdi/dahdi_dynamic_loc.c
parentbc7bdc394a7088d52cd2943039bc6dffd987840a (diff)
dahdi_dynamic_loc: Use a standard kernel linked list.
The memory saved by using a singly linked list does not, in my opinion, outweigh the benefit of using the standard kernel macros. Signed-off-by: Shaun Ruffell <sruffell@digium.com> Acked-by: Kinsey Moore <kmoore@digium.com> git-svn-id: http://svn.asterisk.org/svn/dahdi/linux/trunk@9564 a0bf4364-ded3-4de4-8d8a-66a801d63aff
Diffstat (limited to 'drivers/dahdi/dahdi_dynamic_loc.c')
-rw-r--r--drivers/dahdi/dahdi_dynamic_loc.c92
1 files changed, 40 insertions, 52 deletions
diff --git a/drivers/dahdi/dahdi_dynamic_loc.c b/drivers/dahdi/dahdi_dynamic_loc.c
index 5a5cb02..51a86b8 100644
--- a/drivers/dahdi/dahdi_dynamic_loc.c
+++ b/drivers/dahdi/dahdi_dynamic_loc.c
@@ -57,31 +57,31 @@
#include <dahdi/kernel.h>
-static DEFINE_SPINLOCK(local_lock);
-
/**
* struct dahdi_dynamic_loc - For local dynamic spans
* @monitor_rx_peer: Indicates the peer span that monitors this span.
* @peer: Indicates the rw peer for this span.
*
*/
-static struct dahdi_dynamic_local {
+struct dahdi_dynamic_local {
unsigned short key;
unsigned short id;
struct dahdi_dynamic_local *monitor_rx_peer;
struct dahdi_dynamic_local *peer;
struct dahdi_span *span;
- struct dahdi_dynamic_local *next;
-} *ddevs = NULL;
+ struct list_head node;
+};
+
+static DEFINE_SPINLOCK(local_lock);
+static LIST_HEAD(dynamic_local_list);
static int
dahdi_dynamic_local_transmit(void *pvt, unsigned char *msg, int msglen)
{
- struct dahdi_dynamic_local *d;
+ struct dahdi_dynamic_local *const d = pvt;
unsigned long flags;
spin_lock_irqsave(&local_lock, flags);
- d = pvt;
if (d->peer && d->peer->span)
dahdi_dynamic_receive(d->peer->span, msg, msglen);
if (d->monitor_rx_peer && d->monitor_rx_peer->span)
@@ -126,36 +126,22 @@ static void dahdi_dynamic_local_destroy(void *pvt)
{
struct dahdi_dynamic_local *d = pvt;
unsigned long flags;
- struct dahdi_dynamic_local *prev = NULL, *cur;
+ struct dahdi_dynamic_local *cur;
spin_lock_irqsave(&local_lock, flags);
- cur = ddevs;
- while(cur) {
+ list_for_each_entry(cur, &dynamic_local_list, node) {
if (cur->peer == d)
cur->peer = NULL;
if (cur->monitor_rx_peer == d)
cur->monitor_rx_peer = NULL;
- cur = cur->next;
- }
- cur = ddevs;
- while(cur) {
- if (cur == d) {
- if (prev)
- prev->next = cur->next;
- else
- ddevs = cur->next;
- break;
- }
- prev = cur;
- cur = cur->next;
}
+ list_del(&d->node);
spin_unlock_irqrestore(&local_lock, flags);
- if (cur == d) {
- printk(KERN_INFO "TDMoL: Removed interface for %s, key %d "
- "id %d\n", d->span->name, d->key, d->id);
- module_put(THIS_MODULE);
- kfree(d);
- }
+
+ printk(KERN_INFO "TDMoL: Removed interface for %s, key %d "
+ "id %d\n", d->span->name, d->key, d->id);
+ module_put(THIS_MODULE);
+ kfree(d);
}
static void *dahdi_dynamic_local_create(struct dahdi_span *span, char *address)
@@ -188,33 +174,35 @@ static void *dahdi_dynamic_local_create(struct dahdi_span *span, char *address)
spin_lock_irqsave(&local_lock, flags);
/* Add this peer to any existing spans with same key
And add them as peers to this one */
- for (l = ddevs; l; l = l->next)
- if (l->key == d->key) {
- if (l->id == d->id) {
- printk(KERN_DEBUG "TDMoL: Duplicate id (%d) for key %d\n", d->id, d->key);
+ list_for_each_entry(l, &dynamic_local_list, node) {
+ if (l->key != d->key)
+ continue;
+
+ if (l->id == d->id) {
+ printk(KERN_DEBUG "TDMoL: Duplicate id (%d) for key %d\n", d->id, d->key);
+ goto CLEAR_AND_DEL_FROM_PEERS;
+ }
+ if (monitor == -1) {
+ if (l->peer) {
+ printk(KERN_DEBUG "TDMoL: Span with key %d and id %d already has a R/W peer\n", d->key, d->id);
goto CLEAR_AND_DEL_FROM_PEERS;
+ } else {
+ l->peer = d;
+ d->peer = l;
}
- if (monitor == -1) {
- if (l->peer) {
- printk(KERN_DEBUG "TDMoL: Span with key %d and id %d already has a R/W peer\n", d->key, d->id);
- goto CLEAR_AND_DEL_FROM_PEERS;
- } else {
- l->peer = d;
- d->peer = l;
- }
- }
- if (monitor == l->id) {
- if (l->monitor_rx_peer) {
- printk(KERN_DEBUG "TDMoL: Span with key %d and id %d already has a monitoring peer\n", d->key, d->id);
- goto CLEAR_AND_DEL_FROM_PEERS;
- } else {
- l->monitor_rx_peer = d;
- }
+ }
+ if (monitor == l->id) {
+ if (l->monitor_rx_peer) {
+ printk(KERN_DEBUG "TDMoL: Span with key %d and id %d already has a monitoring peer\n", d->key, d->id);
+ goto CLEAR_AND_DEL_FROM_PEERS;
+ } else {
+ l->monitor_rx_peer = d;
}
}
- d->next = ddevs;
- ddevs = d;
+ }
+ list_add(&d->node, &dynamic_local_list);
spin_unlock_irqrestore(&local_lock, flags);
+
if(!try_module_get(THIS_MODULE))
printk(KERN_DEBUG "TDMoL: Unable to increment module use count\n");
@@ -224,7 +212,7 @@ static void *dahdi_dynamic_local_create(struct dahdi_span *span, char *address)
return d;
CLEAR_AND_DEL_FROM_PEERS:
- for (l = ddevs; l; l = l->next) {
+ list_for_each_entry(l, &dynamic_local_list, node) {
if (l->peer == d)
l->peer = NULL;
if (l->monitor_rx_peer == d)