Commit eff0cf2f authored by Dominik Brodowski's avatar Dominik Brodowski Committed by Linus Torvalds

[PATCH] pcmcia: use pcmcia_device in send_event

Use a struct pcmcia_device-based approach to inform "clients" of events.  It
needs to be done using bus_for_each_device() so that we don't need to take the
device_list spinlock.
Signed-off-by: default avatarDominik Brodowski <linux@brodo.de>
Signed-off-by: default avatarAndrew Morton <akpm@osdl.org>
Signed-off-by: default avatarLinus Torvalds <torvalds@osdl.org>
parent 00bfce19
...@@ -399,8 +399,9 @@ static void shutdown_socket(struct pcmcia_socket *s) ...@@ -399,8 +399,9 @@ static void shutdown_socket(struct pcmcia_socket *s)
/*====================================================================== /*======================================================================
The central event handler. Send_event() sends an event to all The central event handler. Send_event() sends an event to the
valid clients. Parse_events() interprets the event bits from 16-bit subsystem, which then calls the relevant device drivers.
Parse_events() interprets the event bits from
a card status change report. Do_shutdown() handles the high a card status change report. Do_shutdown() handles the high
priority stuff associated with a card removal. priority stuff associated with a card removal.
......
...@@ -537,20 +537,47 @@ static int handle_request(struct pcmcia_bus_socket *s, event_t event) ...@@ -537,20 +537,47 @@ static int handle_request(struct pcmcia_bus_socket *s, event_t event)
======================================================================*/ ======================================================================*/
struct send_event_data {
struct pcmcia_socket *skt;
event_t event;
int priority;
};
static int send_event_callback(struct device *dev, void * _data)
{
struct pcmcia_device *p_dev = to_pcmcia_dev(dev);
struct send_event_data *data = _data;
/* we get called for all sockets, but may only pass the event
* for drivers _on the affected socket_ */
if (p_dev->socket != data->skt)
return 0;
if (p_dev->client->state & (CLIENT_UNBOUND|CLIENT_STALE))
return 0;
if (p_dev->client->EventMask & data->event)
return EVENT(p_dev->client, data->event, data->priority);
return 0;
}
static int send_event(struct pcmcia_socket *s, event_t event, int priority) static int send_event(struct pcmcia_socket *s, event_t event, int priority)
{ {
int ret = 0; int ret = 0;
client_t *client; struct send_event_data private;
struct pcmcia_bus_socket *skt = pcmcia_get_bus_socket(s->pcmcia);
for (client = s->clients; client; client = client->next) { if (!skt)
if (client->state & (CLIENT_UNBOUND|CLIENT_STALE)) return 0;
continue;
if (client->EventMask & event) { private.skt = s;
ret = EVENT(client, event, priority); private.event = event;
if (ret != 0) private.priority = priority;
return ret;
} ret = bus_for_each_dev(&pcmcia_bus_type, NULL, &private, send_event_callback);
}
pcmcia_put_bus_socket(skt);
return ret; return ret;
} /* send_event */ } /* send_event */
......
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