diff options
author | Kristian Høgsberg <krh@redhat.com> | 2006-12-19 19:58:31 -0500 |
---|---|---|
committer | Stefan Richter <stefanr@s5r6.in-berlin.de> | 2007-03-09 16:02:33 -0500 |
commit | 19a15b937b26638933307bb02f7b1801310d6eb2 (patch) | |
tree | 817efaa8c1d2f4633fa811ba27fa1aee7f00c352 /drivers/firewire/fw-card.c | |
parent | 3038e353cfaf548eb94f02b172b9dbe412abd24c (diff) |
firewire: Add device probing and sysfs integration.
Signed-off-by: Kristian Høgsberg <krh@redhat.com>
Signed-off-by: Stefan Richter <stefanr@s5r6.in-berlin.de>
Diffstat (limited to 'drivers/firewire/fw-card.c')
-rw-r--r-- | drivers/firewire/fw-card.c | 56 |
1 files changed, 56 insertions, 0 deletions
diff --git a/drivers/firewire/fw-card.c b/drivers/firewire/fw-card.c index d8abd70ce843..79773907e10d 100644 --- a/drivers/firewire/fw-card.c +++ b/drivers/firewire/fw-card.c | |||
@@ -24,6 +24,7 @@ | |||
24 | #include <linux/device.h> | 24 | #include <linux/device.h> |
25 | #include "fw-transaction.h" | 25 | #include "fw-transaction.h" |
26 | #include "fw-topology.h" | 26 | #include "fw-topology.h" |
27 | #include "fw-device.h" | ||
27 | 28 | ||
28 | /* The lib/crc16.c implementation uses the standard (0x8005) | 29 | /* The lib/crc16.c implementation uses the standard (0x8005) |
29 | * polynomial, but we need the ITU-T (or CCITT) polynomial (0x1021). | 30 | * polynomial, but we need the ITU-T (or CCITT) polynomial (0x1021). |
@@ -186,6 +187,59 @@ fw_core_remove_descriptor (struct fw_descriptor *desc) | |||
186 | EXPORT_SYMBOL(fw_core_remove_descriptor); | 187 | EXPORT_SYMBOL(fw_core_remove_descriptor); |
187 | 188 | ||
188 | static void | 189 | static void |
190 | fw_card_irm_work(struct work_struct *work) | ||
191 | { | ||
192 | struct fw_card *card = | ||
193 | container_of(work, struct fw_card, work.work); | ||
194 | struct fw_device *root; | ||
195 | unsigned long flags; | ||
196 | int new_irm_id, generation; | ||
197 | |||
198 | /* FIXME: This simple bus management unconditionally picks a | ||
199 | * cycle master if the current root can't do it. We need to | ||
200 | * not do this if there is a bus manager already. Also, some | ||
201 | * hubs set the contender bit, which is bogus, so we should | ||
202 | * probably do a little sanity check on the IRM (like, read | ||
203 | * the bandwidth register) if it's not us. */ | ||
204 | |||
205 | spin_lock_irqsave(&card->lock, flags); | ||
206 | |||
207 | generation = card->generation; | ||
208 | root = card->root_node->data; | ||
209 | |||
210 | if (root == NULL) | ||
211 | /* Either link_on is false, or we failed to read the | ||
212 | * config rom. In either case, pick another root. */ | ||
213 | new_irm_id = card->local_node->node_id; | ||
214 | else if (root->state != FW_DEVICE_RUNNING) | ||
215 | /* If we haven't probed this device yet, bail out now | ||
216 | * and let's try again once that's done. */ | ||
217 | new_irm_id = -1; | ||
218 | else if (root->config_rom[2] & bib_cmc) | ||
219 | /* FIXME: I suppose we should set the cmstr bit in the | ||
220 | * STATE_CLEAR register of this node, as described in | ||
221 | * 1394-1995, 8.4.2.6. Also, send out a force root | ||
222 | * packet for this node. */ | ||
223 | new_irm_id = -1; | ||
224 | else | ||
225 | /* Current root has an active link layer and we | ||
226 | * successfully read the config rom, but it's not | ||
227 | * cycle master capable. */ | ||
228 | new_irm_id = card->local_node->node_id; | ||
229 | |||
230 | if (card->irm_retries++ > 5) | ||
231 | new_irm_id = -1; | ||
232 | |||
233 | spin_unlock_irqrestore(&card->lock, flags); | ||
234 | |||
235 | if (new_irm_id > 0) { | ||
236 | fw_notify("Trying to become root (card %d)\n", card->index); | ||
237 | fw_send_force_root(card, new_irm_id, generation); | ||
238 | fw_core_initiate_bus_reset(card, 1); | ||
239 | } | ||
240 | } | ||
241 | |||
242 | static void | ||
189 | release_card(struct device *device) | 243 | release_card(struct device *device) |
190 | { | 244 | { |
191 | struct fw_card *card = | 245 | struct fw_card *card = |
@@ -222,6 +276,8 @@ fw_card_initialize(struct fw_card *card, struct fw_card_driver *driver, | |||
222 | 276 | ||
223 | card->local_node = NULL; | 277 | card->local_node = NULL; |
224 | 278 | ||
279 | INIT_DELAYED_WORK(&card->work, fw_card_irm_work); | ||
280 | |||
225 | card->card_device.bus = &fw_bus_type; | 281 | card->card_device.bus = &fw_bus_type; |
226 | card->card_device.release = release_card; | 282 | card->card_device.release = release_card; |
227 | card->card_device.parent = card->device; | 283 | card->card_device.parent = card->device; |