aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pci
diff options
context:
space:
mode:
authorrajesh.shah@intel.com <rajesh.shah@intel.com>2005-10-31 19:20:06 -0500
committerGreg Kroah-Hartman <gregkh@suse.de>2005-11-10 19:09:14 -0500
commit71b720c0f96145f5868c87591c286b290bc1a6af (patch)
tree797a97084494d99ec59670009242dc25174d3fb1 /drivers/pci
parent24a4e377068d15424cd6a921d41352f295548037 (diff)
[PATCH] patch 1/8] pciehp: use the PCI core for hotplug resource management
This patch converts the pci express hotplug controller driver to use the PCI core for resource management. This eliminates a lot of duplicated code and integrates pciehp with the system's normal PCI handling code. Signed-off-by: Rajesh Shah <rajesh.shah@intel.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
Diffstat (limited to 'drivers/pci')
-rw-r--r--drivers/pci/hotplug/pciehp.h50
-rw-r--r--drivers/pci/hotplug/pciehp_core.c35
-rw-r--r--drivers/pci/hotplug/pciehp_ctrl.c1563
-rw-r--r--drivers/pci/hotplug/pciehp_pci.c487
-rw-r--r--drivers/pci/hotplug/pciehprm_acpi.c840
-rw-r--r--drivers/pci/hotplug/pciehprm_nonacpi.c347
6 files changed, 85 insertions, 3237 deletions
diff --git a/drivers/pci/hotplug/pciehp.h b/drivers/pci/hotplug/pciehp.h
index 061ead21ef14..e9480ddd5abf 100644
--- a/drivers/pci/hotplug/pciehp.h
+++ b/drivers/pci/hotplug/pciehp.h
@@ -59,14 +59,8 @@ struct pci_func {
59 u8 configured; 59 u8 configured;
60 u8 switch_save; 60 u8 switch_save;
61 u8 presence_save; 61 u8 presence_save;
62 u32 base_length[0x06];
63 u8 base_type[0x06];
64 u16 reserved2; 62 u16 reserved2;
65 u32 config_space[0x20]; 63 u32 config_space[0x20];
66 struct pci_resource *mem_head;
67 struct pci_resource *p_mem_head;
68 struct pci_resource *io_head;
69 struct pci_resource *bus_head;
70 struct pci_dev* pci_dev; 64 struct pci_dev* pci_dev;
71}; 65};
72 66
@@ -90,12 +84,6 @@ struct slot {
90 struct list_head slot_list; 84 struct list_head slot_list;
91}; 85};
92 86
93struct pci_resource {
94 struct pci_resource * next;
95 u32 base;
96 u32 length;
97};
98
99struct event_info { 87struct event_info {
100 u32 event_type; 88 u32 event_type;
101 u8 hp_slot; 89 u8 hp_slot;
@@ -107,10 +95,6 @@ struct controller {
107 void *hpc_ctlr_handle; /* HPC controller handle */ 95 void *hpc_ctlr_handle; /* HPC controller handle */
108 int num_slots; /* Number of slots on ctlr */ 96 int num_slots; /* Number of slots on ctlr */
109 int slot_num_inc; /* 1 or -1 */ 97 int slot_num_inc; /* 1 or -1 */
110 struct pci_resource *mem_head;
111 struct pci_resource *p_mem_head;
112 struct pci_resource *io_head;
113 struct pci_resource *bus_head;
114 struct pci_dev *pci_dev; 98 struct pci_dev *pci_dev;
115 struct pci_bus *pci_bus; 99 struct pci_bus *pci_bus;
116 struct event_info event_queue[10]; 100 struct event_info event_queue[10];
@@ -133,20 +117,6 @@ struct controller {
133 u8 cap_base; 117 u8 cap_base;
134}; 118};
135 119
136struct irq_mapping {
137 u8 barber_pole;
138 u8 valid_INT;
139 u8 interrupt[4];
140};
141
142struct resource_lists {
143 struct pci_resource *mem_head;
144 struct pci_resource *p_mem_head;
145 struct pci_resource *io_head;
146 struct pci_resource *bus_head;
147 struct irq_mapping *irqs;
148};
149
150#define INT_BUTTON_IGNORE 0 120#define INT_BUTTON_IGNORE 0
151#define INT_PRESENCE_ON 1 121#define INT_PRESENCE_ON 1
152#define INT_PRESENCE_OFF 2 122#define INT_PRESENCE_OFF 2
@@ -203,14 +173,12 @@ struct resource_lists {
203#define msg_HPC_rev_error "Unsupported revision of the PCI hot plug controller found.\n" 173#define msg_HPC_rev_error "Unsupported revision of the PCI hot plug controller found.\n"
204#define msg_HPC_non_pcie "The PCI hot plug controller is not supported by this driver.\n" 174#define msg_HPC_non_pcie "The PCI hot plug controller is not supported by this driver.\n"
205#define msg_HPC_not_supported "This system is not supported by this version of pciephd module. Upgrade to a newer version of pciehpd\n" 175#define msg_HPC_not_supported "This system is not supported by this version of pciephd module. Upgrade to a newer version of pciehpd\n"
206#define msg_unable_to_save "Unable to store PCI hot plug add resource information. This system must be rebooted before adding any PCI devices.\n"
207#define msg_button_on "PCI slot #%d - powering on due to button press.\n" 176#define msg_button_on "PCI slot #%d - powering on due to button press.\n"
208#define msg_button_off "PCI slot #%d - powering off due to button press.\n" 177#define msg_button_off "PCI slot #%d - powering off due to button press.\n"
209#define msg_button_cancel "PCI slot #%d - action canceled due to button press.\n" 178#define msg_button_cancel "PCI slot #%d - action canceled due to button press.\n"
210#define msg_button_ignore "PCI slot #%d - button press ignored. (action in progress...)\n" 179#define msg_button_ignore "PCI slot #%d - button press ignored. (action in progress...)\n"
211 180
212/* controller functions */ 181/* controller functions */
213extern int pciehprm_find_available_resources (struct controller *ctrl);
214extern int pciehp_event_start_thread (void); 182extern int pciehp_event_start_thread (void);
215extern void pciehp_event_stop_thread (void); 183extern void pciehp_event_stop_thread (void);
216extern struct pci_func *pciehp_slot_create (unsigned char busnumber); 184extern struct pci_func *pciehp_slot_create (unsigned char busnumber);
@@ -224,19 +192,12 @@ extern u8 pciehp_handle_presence_change (u8 hp_slot, void *inst_id);
224extern u8 pciehp_handle_power_fault (u8 hp_slot, void *inst_id); 192extern u8 pciehp_handle_power_fault (u8 hp_slot, void *inst_id);
225/* extern void long_delay (int delay); */ 193/* extern void long_delay (int delay); */
226 194
227/* resource functions */
228extern int pciehp_resource_sort_and_combine (struct pci_resource **head);
229
230/* pci functions */ 195/* pci functions */
231extern int pciehp_set_irq (u8 bus_num, u8 dev_num, u8 int_pin, u8 irq_num); 196extern int pciehp_set_irq (u8 bus_num, u8 dev_num, u8 int_pin, u8 irq_num);
232/*extern int pciehp_get_bus_dev (struct controller *ctrl, u8 *bus_num, u8 *dev_num, struct slot *slot);*/ 197/*extern int pciehp_get_bus_dev (struct controller *ctrl, u8 *bus_num, u8 *dev_num, struct slot *slot);*/
233extern int pciehp_save_config (struct controller *ctrl, int busnumber, int num_ctlr_slots, int first_device_num); 198extern int pciehp_save_config (struct controller *ctrl, int busnumber, int num_ctlr_slots, int first_device_num);
234extern int pciehp_save_used_resources (struct controller *ctrl, struct pci_func * func, int flag);
235extern int pciehp_save_slot_config (struct controller *ctrl, struct pci_func * new_slot); 199extern int pciehp_save_slot_config (struct controller *ctrl, struct pci_func * new_slot);
236extern void pciehp_destroy_board_resources (struct pci_func * func); 200extern int pciehp_configure_device (struct slot *ctrl);
237extern int pciehp_return_board_resources (struct pci_func * func, struct resource_lists * resources);
238extern void pciehp_destroy_resource_list (struct resource_lists * resources);
239extern int pciehp_configure_device (struct controller* ctrl, struct pci_func* func);
240extern int pciehp_unconfigure_device (struct pci_func* func); 201extern int pciehp_unconfigure_device (struct pci_func* func);
241 202
242 203
@@ -289,15 +250,6 @@ static inline int wait_for_ctrl_irq(struct controller *ctrl)
289 return retval; 250 return retval;
290} 251}
291 252
292/* Puts node back in the resource list pointed to by head */
293static inline void return_resource(struct pci_resource **head, struct pci_resource *node)
294{
295 if (!node || !head)
296 return;
297 node->next = *head;
298 *head = node;
299}
300
301#define SLOT_NAME_SIZE 10 253#define SLOT_NAME_SIZE 10
302 254
303static inline void make_slot_name(char *buffer, int buffer_size, struct slot *slot) 255static inline void make_slot_name(char *buffer, int buffer_size, struct slot *slot)
diff --git a/drivers/pci/hotplug/pciehp_core.c b/drivers/pci/hotplug/pciehp_core.c
index cafc7eadcf80..190664e5adf4 100644
--- a/drivers/pci/hotplug/pciehp_core.c
+++ b/drivers/pci/hotplug/pciehp_core.c
@@ -433,16 +433,8 @@ static int pciehp_probe(struct pcie_device *dev, const struct pcie_port_service_
433 goto err_out_free_ctrl_bus; 433 goto err_out_free_ctrl_bus;
434 } 434 }
435 435
436 /* Get IO, memory, and IRQ resources for new devices */ 436 ctrl->add_support = 1;
437 rc = pciehprm_find_available_resources(ctrl);
438 ctrl->add_support = !rc;
439 437
440 if (rc) {
441 dbg("pciehprm_find_available_resources = %#x\n", rc);
442 err("unable to locate PCI configuration resources for hot plug add.\n");
443 goto err_out_free_ctrl_bus;
444 }
445
446 /* Setup the slot information structures */ 438 /* Setup the slot information structures */
447 rc = init_slots(ctrl); 439 rc = init_slots(ctrl);
448 if (rc) { 440 if (rc) {
@@ -521,18 +513,6 @@ static int pcie_start_thread(void)
521 return retval; 513 return retval;
522} 514}
523 515
524static inline void __exit
525free_pciehp_res(struct pci_resource *res)
526{
527 struct pci_resource *tres;
528
529 while (res) {
530 tres = res;
531 res = res->next;
532 kfree(tres);
533 }
534}
535
536static void __exit unload_pciehpd(void) 516static void __exit unload_pciehpd(void)
537{ 517{
538 struct pci_func *next; 518 struct pci_func *next;
@@ -546,11 +526,6 @@ static void __exit unload_pciehpd(void)
546 while (ctrl) { 526 while (ctrl) {
547 cleanup_slots(ctrl); 527 cleanup_slots(ctrl);
548 528
549 free_pciehp_res(ctrl->io_head);
550 free_pciehp_res(ctrl->mem_head);
551 free_pciehp_res(ctrl->p_mem_head);
552 free_pciehp_res(ctrl->bus_head);
553
554 kfree (ctrl->pci_bus); 529 kfree (ctrl->pci_bus);
555 530
556 ctrl->hpc_ops->release_ctlr(ctrl); 531 ctrl->hpc_ops->release_ctlr(ctrl);
@@ -564,11 +539,6 @@ static void __exit unload_pciehpd(void)
564 for (loop = 0; loop < 256; loop++) { 539 for (loop = 0; loop < 256; loop++) {
565 next = pciehp_slot_list[loop]; 540 next = pciehp_slot_list[loop];
566 while (next != NULL) { 541 while (next != NULL) {
567 free_pciehp_res(next->io_head);
568 free_pciehp_res(next->mem_head);
569 free_pciehp_res(next->p_mem_head);
570 free_pciehp_res(next->bus_head);
571
572 TempSlot = next; 542 TempSlot = next;
573 next = next->next; 543 next = next->next;
574 kfree(TempSlot); 544 kfree(TempSlot);
@@ -652,8 +622,7 @@ error_hpc_init:
652 if (retval) { 622 if (retval) {
653 pciehprm_cleanup(); 623 pciehprm_cleanup();
654 pciehp_event_stop_thread(); 624 pciehp_event_stop_thread();
655 } else 625 };
656 pciehprm_print_pirt();
657 626
658 return retval; 627 return retval;
659} 628}
diff --git a/drivers/pci/hotplug/pciehp_ctrl.c b/drivers/pci/hotplug/pciehp_ctrl.c
index 898f6da6f0de..412783e0ef40 100644
--- a/drivers/pci/hotplug/pciehp_ctrl.c
+++ b/drivers/pci/hotplug/pciehp_ctrl.c
@@ -42,10 +42,6 @@
42#include "pciehp.h" 42#include "pciehp.h"
43#include "pciehprm.h" 43#include "pciehprm.h"
44 44
45static u32 configure_new_device(struct controller *ctrl, struct pci_func *func,
46 u8 behind_bridge, struct resource_lists *resources, u8 bridge_bus, u8 bridge_dev);
47static int configure_new_function( struct controller *ctrl, struct pci_func *func,
48 u8 behind_bridge, struct resource_lists *resources, u8 bridge_bus, u8 bridge_dev);
49static void interrupt_event_handler(struct controller *ctrl); 45static void interrupt_event_handler(struct controller *ctrl);
50 46
51static struct semaphore event_semaphore; /* mutex for process loop (up if something to process) */ 47static struct semaphore event_semaphore; /* mutex for process loop (up if something to process) */
@@ -252,627 +248,6 @@ u8 pciehp_handle_power_fault(u8 hp_slot, void *inst_id)
252 return rc; 248 return rc;
253} 249}
254 250
255
256/**
257 * sort_by_size: sort nodes by their length, smallest first.
258 *
259 * @head: list to sort
260 */
261static int sort_by_size(struct pci_resource **head)
262{
263 struct pci_resource *current_res;
264 struct pci_resource *next_res;
265 int out_of_order = 1;
266
267 if (!(*head))
268 return 1;
269
270 if (!((*head)->next))
271 return 0;
272
273 while (out_of_order) {
274 out_of_order = 0;
275
276 /* Special case for swapping list head */
277 if (((*head)->next) &&
278 ((*head)->length > (*head)->next->length)) {
279 out_of_order++;
280 current_res = *head;
281 *head = (*head)->next;
282 current_res->next = (*head)->next;
283 (*head)->next = current_res;
284 }
285
286 current_res = *head;
287
288 while (current_res->next && current_res->next->next) {
289 if (current_res->next->length > current_res->next->next->length) {
290 out_of_order++;
291 next_res = current_res->next;
292 current_res->next = current_res->next->next;
293 current_res = current_res->next;
294 next_res->next = current_res->next;
295 current_res->next = next_res;
296 } else
297 current_res = current_res->next;
298 }
299 } /* End of out_of_order loop */
300
301 return 0;
302}
303
304
305/*
306 * sort_by_max_size
307 *
308 * Sorts nodes on the list by their length.
309 * Largest first.
310 *
311 */
312static int sort_by_max_size(struct pci_resource **head)
313{
314 struct pci_resource *current_res;
315 struct pci_resource *next_res;
316 int out_of_order = 1;
317
318 if (!(*head))
319 return 1;
320
321 if (!((*head)->next))
322 return 0;
323
324 while (out_of_order) {
325 out_of_order = 0;
326
327 /* Special case for swapping list head */
328 if (((*head)->next) &&
329 ((*head)->length < (*head)->next->length)) {
330 out_of_order++;
331 current_res = *head;
332 *head = (*head)->next;
333 current_res->next = (*head)->next;
334 (*head)->next = current_res;
335 }
336
337 current_res = *head;
338
339 while (current_res->next && current_res->next->next) {
340 if (current_res->next->length < current_res->next->next->length) {
341 out_of_order++;
342 next_res = current_res->next;
343 current_res->next = current_res->next->next;
344 current_res = current_res->next;
345 next_res->next = current_res->next;
346 current_res->next = next_res;
347 } else
348 current_res = current_res->next;
349 }
350 } /* End of out_of_order loop */
351
352 return 0;
353}
354
355
356/**
357 * do_pre_bridge_resource_split: return one unused resource node
358 * @head: list to scan
359 *
360 */
361static struct pci_resource *
362do_pre_bridge_resource_split(struct pci_resource **head,
363 struct pci_resource **orig_head, u32 alignment)
364{
365 struct pci_resource *prevnode = NULL;
366 struct pci_resource *node;
367 struct pci_resource *split_node;
368 u32 rc;
369 u32 temp_dword;
370 dbg("do_pre_bridge_resource_split\n");
371
372 if (!(*head) || !(*orig_head))
373 return NULL;
374
375 rc = pciehp_resource_sort_and_combine(head);
376
377 if (rc)
378 return NULL;
379
380 if ((*head)->base != (*orig_head)->base)
381 return NULL;
382
383 if ((*head)->length == (*orig_head)->length)
384 return NULL;
385
386
387 /* If we got here, there the bridge requires some of the resource, but
388 * we may be able to split some off of the front
389 */
390 node = *head;
391
392 if (node->length & (alignment -1)) {
393 /* this one isn't an aligned length, so we'll make a new entry
394 * and split it up.
395 */
396 split_node = kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
397
398 if (!split_node)
399 return NULL;
400
401 temp_dword = (node->length | (alignment-1)) + 1 - alignment;
402
403 split_node->base = node->base;
404 split_node->length = temp_dword;
405
406 node->length -= temp_dword;
407 node->base += split_node->length;
408
409 /* Put it in the list */
410 *head = split_node;
411 split_node->next = node;
412 }
413
414 if (node->length < alignment)
415 return NULL;
416
417 /* Now unlink it */
418 if (*head == node) {
419 *head = node->next;
420 } else {
421 prevnode = *head;
422 while (prevnode->next != node)
423 prevnode = prevnode->next;
424
425 prevnode->next = node->next;
426 }
427 node->next = NULL;
428
429 return node;
430}
431
432
433/**
434 * do_bridge_resource_split: return one unused resource node
435 * @head: list to scan
436 *
437 */
438static struct pci_resource *
439do_bridge_resource_split(struct pci_resource **head, u32 alignment)
440{
441 struct pci_resource *prevnode = NULL;
442 struct pci_resource *node;
443 u32 rc;
444 u32 temp_dword;
445
446 if (!(*head))
447 return NULL;
448
449 rc = pciehp_resource_sort_and_combine(head);
450
451 if (rc)
452 return NULL;
453
454 node = *head;
455
456 while (node->next) {
457 prevnode = node;
458 node = node->next;
459 kfree(prevnode);
460 }
461
462 if (node->length < alignment) {
463 kfree(node);
464 return NULL;
465 }
466
467 if (node->base & (alignment - 1)) {
468 /* Short circuit if adjusted size is too small */
469 temp_dword = (node->base | (alignment-1)) + 1;
470 if ((node->length - (temp_dword - node->base)) < alignment) {
471 kfree(node);
472 return NULL;
473 }
474
475 node->length -= (temp_dword - node->base);
476 node->base = temp_dword;
477 }
478
479 if (node->length & (alignment - 1)) {
480 /* There's stuff in use after this node */
481 kfree(node);
482 return NULL;
483 }
484
485 return node;
486}
487
488
489/*
490 * get_io_resource
491 *
492 * this function sorts the resource list by size and then
493 * returns the first node of "size" length that is not in the
494 * ISA aliasing window. If it finds a node larger than "size"
495 * it will split it up.
496 *
497 * size must be a power of two.
498 */
499static struct pci_resource *get_io_resource(struct pci_resource **head, u32 size)
500{
501 struct pci_resource *prevnode;
502 struct pci_resource *node;
503 struct pci_resource *split_node = NULL;
504 u32 temp_dword;
505
506 if (!(*head))
507 return NULL;
508
509 if ( pciehp_resource_sort_and_combine(head) )
510 return NULL;
511
512 if ( sort_by_size(head) )
513 return NULL;
514
515 for (node = *head; node; node = node->next) {
516 if (node->length < size)
517 continue;
518
519 if (node->base & (size - 1)) {
520 /* this one isn't base aligned properly
521 so we'll make a new entry and split it up */
522 temp_dword = (node->base | (size-1)) + 1;
523
524 /*/ Short circuit if adjusted size is too small */
525 if ((node->length - (temp_dword - node->base)) < size)
526 continue;
527
528 split_node = kmalloc(sizeof(struct pci_resource),
529 GFP_KERNEL);
530
531 if (!split_node)
532 return NULL;
533
534 split_node->base = node->base;
535 split_node->length = temp_dword - node->base;
536 node->base = temp_dword;
537 node->length -= split_node->length;
538
539 /* Put it in the list */
540 split_node->next = node->next;
541 node->next = split_node;
542 } /* End of non-aligned base */
543
544 /* Don't need to check if too small since we already did */
545 if (node->length > size) {
546 /* this one is longer than we need
547 so we'll make a new entry and split it up */
548 split_node = kmalloc(sizeof(struct pci_resource),
549 GFP_KERNEL);
550
551 if (!split_node)
552 return NULL;
553
554 split_node->base = node->base + size;
555 split_node->length = node->length - size;
556 node->length = size;
557
558 /* Put it in the list */
559 split_node->next = node->next;
560 node->next = split_node;
561 } /* End of too big on top end */
562
563 /* For IO make sure it's not in the ISA aliasing space */
564 if (node->base & 0x300L)
565 continue;
566
567 /* If we got here, then it is the right size
568 Now take it out of the list */
569 if (*head == node) {
570 *head = node->next;
571 } else {
572 prevnode = *head;
573 while (prevnode->next != node)
574 prevnode = prevnode->next;
575
576 prevnode->next = node->next;
577 }
578 node->next = NULL;
579 /* Stop looping */
580 break;
581 }
582
583 return node;
584}
585
586
587/*
588 * get_max_resource
589 *
590 * Gets the largest node that is at least "size" big from the
591 * list pointed to by head. It aligns the node on top and bottom
592 * to "size" alignment before returning it.
593 * J.I. modified to put max size limits of; 64M->32M->16M->8M->4M->1M
594 * This is needed to avoid allocating entire ACPI _CRS res to one child bridge/slot.
595 */
596static struct pci_resource *get_max_resource(struct pci_resource **head, u32 size)
597{
598 struct pci_resource *max;
599 struct pci_resource *temp;
600 struct pci_resource *split_node;
601 u32 temp_dword;
602 u32 max_size[] = { 0x4000000, 0x2000000, 0x1000000, 0x0800000, 0x0400000, 0x0200000, 0x0100000, 0x00 };
603 int i;
604
605 if (!(*head))
606 return NULL;
607
608 if (pciehp_resource_sort_and_combine(head))
609 return NULL;
610
611 if (sort_by_max_size(head))
612 return NULL;
613
614 for (max = *head;max; max = max->next) {
615
616 /* If not big enough we could probably just bail,
617 instead we'll continue to the next. */
618 if (max->length < size)
619 continue;
620
621 if (max->base & (size - 1)) {
622 /* this one isn't base aligned properly
623 so we'll make a new entry and split it up */
624 temp_dword = (max->base | (size-1)) + 1;
625
626 /* Short circuit if adjusted size is too small */
627 if ((max->length - (temp_dword - max->base)) < size)
628 continue;
629
630 split_node = kmalloc(sizeof(struct pci_resource),
631 GFP_KERNEL);
632
633 if (!split_node)
634 return NULL;
635
636 split_node->base = max->base;
637 split_node->length = temp_dword - max->base;
638 max->base = temp_dword;
639 max->length -= split_node->length;
640
641 /* Put it next in the list */
642 split_node->next = max->next;
643 max->next = split_node;
644 }
645
646 if ((max->base + max->length) & (size - 1)) {
647 /* this one isn't end aligned properly at the top
648 so we'll make a new entry and split it up */
649 split_node = kmalloc(sizeof(struct pci_resource),
650 GFP_KERNEL);
651
652 if (!split_node)
653 return NULL;
654 temp_dword = ((max->base + max->length) & ~(size - 1));
655 split_node->base = temp_dword;
656 split_node->length = max->length + max->base
657 - split_node->base;
658 max->length -= split_node->length;
659
660 /* Put it in the list */
661 split_node->next = max->next;
662 max->next = split_node;
663 }
664
665 /* Make sure it didn't shrink too much when we aligned it */
666 if (max->length < size)
667 continue;
668
669 for ( i = 0; max_size[i] > size; i++) {
670 if (max->length > max_size[i]) {
671 split_node = kmalloc(sizeof(struct pci_resource),
672 GFP_KERNEL);
673 if (!split_node)
674 break; /* return NULL; */
675 split_node->base = max->base + max_size[i];
676 split_node->length = max->length - max_size[i];
677 max->length = max_size[i];
678 /* Put it next in the list */
679 split_node->next = max->next;
680 max->next = split_node;
681 break;
682 }
683 }
684
685 /* Now take it out of the list */
686 temp = (struct pci_resource*) *head;
687 if (temp == max) {
688 *head = max->next;
689 } else {
690 while (temp && temp->next != max) {
691 temp = temp->next;
692 }
693
694 temp->next = max->next;
695 }
696
697 max->next = NULL;
698 return max;
699 }
700
701 /* If we get here, we couldn't find one */
702 return NULL;
703}
704
705
706/*
707 * get_resource
708 *
709 * this function sorts the resource list by size and then
710 * returns the first node of "size" length. If it finds a node
711 * larger than "size" it will split it up.
712 *
713 * size must be a power of two.
714 */
715static struct pci_resource *get_resource(struct pci_resource **head, u32 size)
716{
717 struct pci_resource *prevnode;
718 struct pci_resource *node;
719 struct pci_resource *split_node;
720 u32 temp_dword;
721
722 if (!(*head))
723 return NULL;
724
725 if ( pciehp_resource_sort_and_combine(head) )
726 return NULL;
727
728 if ( sort_by_size(head) )
729 return NULL;
730
731 for (node = *head; node; node = node->next) {
732 dbg("%s: req_size =0x%x node=%p, base=0x%x, length=0x%x\n",
733 __FUNCTION__, size, node, node->base, node->length);
734 if (node->length < size)
735 continue;
736
737 if (node->base & (size - 1)) {
738 dbg("%s: not aligned\n", __FUNCTION__);
739 /* this one isn't base aligned properly
740 so we'll make a new entry and split it up */
741 temp_dword = (node->base | (size-1)) + 1;
742
743 /* Short circuit if adjusted size is too small */
744 if ((node->length - (temp_dword - node->base)) < size)
745 continue;
746
747 split_node = kmalloc(sizeof(struct pci_resource),
748 GFP_KERNEL);
749
750 if (!split_node)
751 return NULL;
752
753 split_node->base = node->base;
754 split_node->length = temp_dword - node->base;
755 node->base = temp_dword;
756 node->length -= split_node->length;
757
758 /* Put it in the list */
759 split_node->next = node->next;
760 node->next = split_node;
761 } /* End of non-aligned base */
762
763 /* Don't need to check if too small since we already did */
764 if (node->length > size) {
765 dbg("%s: too big\n", __FUNCTION__);
766 /* this one is longer than we need
767 so we'll make a new entry and split it up */
768 split_node = kmalloc(sizeof(struct pci_resource),
769 GFP_KERNEL);
770
771 if (!split_node)
772 return NULL;
773
774 split_node->base = node->base + size;
775 split_node->length = node->length - size;
776 node->length = size;
777
778 /* Put it in the list */
779 split_node->next = node->next;
780 node->next = split_node;
781 } /* End of too big on top end */
782
783 dbg("%s: got one!!!\n", __FUNCTION__);
784 /* If we got here, then it is the right size
785 Now take it out of the list */
786 if (*head == node) {
787 *head = node->next;
788 } else {
789 prevnode = *head;
790 while (prevnode->next != node)
791 prevnode = prevnode->next;
792
793 prevnode->next = node->next;
794 }
795 node->next = NULL;
796 /* Stop looping */
797 break;
798 }
799 return node;
800}
801
802
803/*
804 * pciehp_resource_sort_and_combine
805 *
806 * Sorts all of the nodes in the list in ascending order by
807 * their base addresses. Also does garbage collection by
808 * combining adjacent nodes.
809 *
810 * returns 0 if success
811 */
812int pciehp_resource_sort_and_combine(struct pci_resource **head)
813{
814 struct pci_resource *node1;
815 struct pci_resource *node2;
816 int out_of_order = 1;
817
818 dbg("%s: head = %p, *head = %p\n", __FUNCTION__, head, *head);
819
820 if (!(*head))
821 return 1;
822
823 dbg("*head->next = %p\n",(*head)->next);
824
825 if (!(*head)->next)
826 return 0; /* only one item on the list, already sorted! */
827
828 dbg("*head->base = 0x%x\n",(*head)->base);
829 dbg("*head->next->base = 0x%x\n",(*head)->next->base);
830 while (out_of_order) {
831 out_of_order = 0;
832
833 /* Special case for swapping list head */
834 if (((*head)->next) &&
835 ((*head)->base > (*head)->next->base)) {
836 node1 = *head;
837 (*head) = (*head)->next;
838 node1->next = (*head)->next;
839 (*head)->next = node1;
840 out_of_order++;
841 }
842
843 node1 = (*head);
844
845 while (node1->next && node1->next->next) {
846 if (node1->next->base > node1->next->next->base) {
847 out_of_order++;
848 node2 = node1->next;
849 node1->next = node1->next->next;
850 node1 = node1->next;
851 node2->next = node1->next;
852 node1->next = node2;
853 } else
854 node1 = node1->next;
855 }
856 } /* End of out_of_order loop */
857
858 node1 = *head;
859
860 while (node1 && node1->next) {
861 if ((node1->base + node1->length) == node1->next->base) {
862 /* Combine */
863 dbg("8..\n");
864 node1->length += node1->next->length;
865 node2 = node1->next;
866 node1->next = node1->next->next;
867 kfree(node2);
868 } else
869 node1 = node1->next;
870 }
871
872 return 0;
873}
874
875
876/** 251/**
877 * pciehp_slot_create - Creates a node and adds it to the proper bus. 252 * pciehp_slot_create - Creates a node and adds it to the proper bus.
878 * @busnumber - bus where new node is to be located 253 * @busnumber - bus where new node is to be located
@@ -926,7 +301,6 @@ static int slot_remove(struct pci_func * old_slot)
926 301
927 if (next == old_slot) { 302 if (next == old_slot) {
928 pciehp_slot_list[old_slot->bus] = old_slot->next; 303 pciehp_slot_list[old_slot->bus] = old_slot->next;
929 pciehp_destroy_board_resources(old_slot);
930 kfree(old_slot); 304 kfree(old_slot);
931 return 0; 305 return 0;
932 } 306 }
@@ -937,7 +311,6 @@ static int slot_remove(struct pci_func * old_slot)
937 311
938 if (next->next == old_slot) { 312 if (next->next == old_slot) {
939 next->next = old_slot->next; 313 next->next = old_slot->next;
940 pciehp_destroy_board_resources(old_slot);
941 kfree(old_slot); 314 kfree(old_slot);
942 return 0; 315 return 0;
943 } else 316 } else
@@ -1103,12 +476,9 @@ static void set_slot_off(struct controller *ctrl, struct slot * pslot)
1103static u32 board_added(struct pci_func * func, struct controller * ctrl) 476static u32 board_added(struct pci_func * func, struct controller * ctrl)
1104{ 477{
1105 u8 hp_slot; 478 u8 hp_slot;
1106 int index;
1107 u32 temp_register = 0xFFFFFFFF; 479 u32 temp_register = 0xFFFFFFFF;
1108 u32 rc = 0; 480 u32 rc = 0;
1109 struct pci_func *new_func = NULL;
1110 struct slot *p_slot; 481 struct slot *p_slot;
1111 struct resource_lists res_lists;
1112 482
1113 p_slot = pciehp_find_slot(ctrl, func->device); 483 p_slot = pciehp_find_slot(ctrl, func->device);
1114 hp_slot = func->device - ctrl->slot_device_offset; 484 hp_slot = func->device - ctrl->slot_device_offset;
@@ -1162,89 +532,43 @@ static u32 board_added(struct pci_func * func, struct controller * ctrl)
1162 dbg("%s: temp register set to %x by power fault\n", __FUNCTION__, temp_register); 532 dbg("%s: temp register set to %x by power fault\n", __FUNCTION__, temp_register);
1163 rc = POWER_FAILURE; 533 rc = POWER_FAILURE;
1164 func->status = 0; 534 func->status = 0;
1165 } else { 535 goto err_exit;
1166 /* Get vendor/device ID u32 */
1167 rc = pci_bus_read_config_dword (ctrl->pci_dev->subordinate, PCI_DEVFN(func->device, func->function),
1168 PCI_VENDOR_ID, &temp_register);
1169 dbg("%s: pci_bus_read_config_dword returns %d\n", __FUNCTION__, rc);
1170 dbg("%s: temp_register is %x\n", __FUNCTION__, temp_register);
1171
1172 if (rc != 0) {
1173 /* Something's wrong here */
1174 temp_register = 0xFFFFFFFF;
1175 dbg("%s: temp register set to %x by error\n", __FUNCTION__, temp_register);
1176 }
1177 /* Preset return code. It will be changed later if things go okay. */
1178 rc = NO_ADAPTER_PRESENT;
1179 } 536 }
1180 537
1181 /* All F's is an empty slot or an invalid board */ 538 rc = pciehp_configure_device(p_slot);
1182 if (temp_register != 0xFFFFFFFF) { /* Check for a board in the slot */ 539 if (rc) {
1183 res_lists.io_head = ctrl->io_head; 540 err("Cannot add device 0x%x:%x\n", p_slot->bus,
1184 res_lists.mem_head = ctrl->mem_head; 541 p_slot->device);
1185 res_lists.p_mem_head = ctrl->p_mem_head; 542 goto err_exit;
1186 res_lists.bus_head = ctrl->bus_head; 543 }
1187 res_lists.irqs = NULL;
1188
1189 rc = configure_new_device(ctrl, func, 0, &res_lists, 0, 0);
1190 dbg("%s: back from configure_new_device\n", __FUNCTION__);
1191
1192 ctrl->io_head = res_lists.io_head;
1193 ctrl->mem_head = res_lists.mem_head;
1194 ctrl->p_mem_head = res_lists.p_mem_head;
1195 ctrl->bus_head = res_lists.bus_head;
1196
1197 pciehp_resource_sort_and_combine(&(ctrl->mem_head));
1198 pciehp_resource_sort_and_combine(&(ctrl->p_mem_head));
1199 pciehp_resource_sort_and_combine(&(ctrl->io_head));
1200 pciehp_resource_sort_and_combine(&(ctrl->bus_head));
1201 544
1202 if (rc) { 545 pciehp_save_slot_config(ctrl, func);
1203 set_slot_off(ctrl, p_slot); 546 func->status = 0;
1204 return rc; 547 func->switch_save = 0x10;
1205 } 548 func->is_a_board = 0x01;
1206 pciehp_save_slot_config(ctrl, func);
1207 549
1208 func->status = 0; 550 /*
1209 func->switch_save = 0x10; 551 * Some PCI Express root ports require fixup after hot-plug operation.
1210 func->is_a_board = 0x01; 552 */
553 if (pcie_mch_quirk)
554 pci_fixup_device(pci_fixup_final, ctrl->pci_dev);
555 if (PWR_LED(ctrl->ctrlcap)) {
556 /* Wait for exclusive access to hardware */
557 down(&ctrl->crit_sect);
1211 558
1212 /* next, we will instantiate the linux pci_dev structures 559 p_slot->hpc_ops->green_led_on(p_slot);
1213 * (with appropriate driver notification, if already present)
1214 */
1215 index = 0;
1216 do {
1217 new_func = pciehp_slot_find(ctrl->slot_bus, func->device, index++);
1218 if (new_func && !new_func->pci_dev) {
1219 dbg("%s:call pci_hp_configure_dev, func %x\n",
1220 __FUNCTION__, index);
1221 pciehp_configure_device(ctrl, new_func);
1222 }
1223 } while (new_func);
1224
1225 /*
1226 * Some PCI Express root ports require fixup after hot-plug operation.
1227 */
1228 if (pcie_mch_quirk)
1229 pci_fixup_device(pci_fixup_final, ctrl->pci_dev);
1230
1231 if (PWR_LED(ctrl->ctrlcap)) {
1232 /* Wait for exclusive access to hardware */
1233 down(&ctrl->crit_sect);
1234
1235 p_slot->hpc_ops->green_led_on(p_slot);
1236 560
1237 /* Wait for the command to complete */ 561 /* Wait for the command to complete */
1238 wait_for_ctrl_irq (ctrl); 562 wait_for_ctrl_irq (ctrl);
1239 563
1240 /* Done with exclusive hardware access */ 564 /* Done with exclusive hardware access */
1241 up(&ctrl->crit_sect); 565 up(&ctrl->crit_sect);
1242 } 566 }
1243 } else {
1244 set_slot_off(ctrl, p_slot);
1245 return -1;
1246 }
1247 return 0; 567 return 0;
568
569err_exit:
570 set_slot_off(ctrl, p_slot);
571 return -1;
1248} 572}
1249 573
1250 574
@@ -1254,13 +578,9 @@ static u32 board_added(struct pci_func * func, struct controller * ctrl)
1254 */ 578 */
1255static u32 remove_board(struct pci_func *func, struct controller *ctrl) 579static u32 remove_board(struct pci_func *func, struct controller *ctrl)
1256{ 580{
1257 int index;
1258 u8 skip = 0;
1259 u8 device; 581 u8 device;
1260 u8 hp_slot; 582 u8 hp_slot;
1261 u32 rc; 583 u32 rc;
1262 struct resource_lists res_lists;
1263 struct pci_func *temp_func;
1264 struct slot *p_slot; 584 struct slot *p_slot;
1265 585
1266 if (func == NULL) 586 if (func == NULL)
@@ -1276,27 +596,6 @@ static u32 remove_board(struct pci_func *func, struct controller *ctrl)
1276 596
1277 dbg("In %s, hp_slot = %d\n", __FUNCTION__, hp_slot); 597 dbg("In %s, hp_slot = %d\n", __FUNCTION__, hp_slot);
1278 598
1279 if ((ctrl->add_support) &&
1280 !(func->bus_head || func->mem_head || func->p_mem_head || func->io_head)) {
1281 /* Here we check to see if we've saved any of the board's
1282 * resources already. If so, we'll skip the attempt to
1283 * determine what's being used.
1284 */
1285 index = 0;
1286
1287 temp_func = func;
1288
1289 while ((temp_func = pciehp_slot_find(temp_func->bus, temp_func->device, index++))) {
1290 if (temp_func->bus_head || temp_func->mem_head
1291 || temp_func->p_mem_head || temp_func->io_head) {
1292 skip = 1;
1293 break;
1294 }
1295 }
1296
1297 if (!skip)
1298 rc = pciehp_save_used_resources(ctrl, func, DISABLE_CARD);
1299 }
1300 /* Change status to shutdown */ 599 /* Change status to shutdown */
1301 if (func->is_a_board) 600 if (func->is_a_board)
1302 func->status = 0x01; 601 func->status = 0x01;
@@ -1330,26 +629,6 @@ static u32 remove_board(struct pci_func *func, struct controller *ctrl)
1330 629
1331 if (ctrl->add_support) { 630 if (ctrl->add_support) {
1332 while (func) { 631 while (func) {
1333 res_lists.io_head = ctrl->io_head;
1334 res_lists.mem_head = ctrl->mem_head;
1335 res_lists.p_mem_head = ctrl->p_mem_head;
1336 res_lists.bus_head = ctrl->bus_head;
1337
1338 dbg("Returning resources to ctlr lists for (B/D/F) = (%#x/%#x/%#x)\n",
1339 func->bus, func->device, func->function);
1340
1341 pciehp_return_board_resources(func, &res_lists);
1342
1343 ctrl->io_head = res_lists.io_head;
1344 ctrl->mem_head = res_lists.mem_head;
1345 ctrl->p_mem_head = res_lists.p_mem_head;
1346 ctrl->bus_head = res_lists.bus_head;
1347
1348 pciehp_resource_sort_and_combine(&(ctrl->mem_head));
1349 pciehp_resource_sort_and_combine(&(ctrl->p_mem_head));
1350 pciehp_resource_sort_and_combine(&(ctrl->io_head));
1351 pciehp_resource_sort_and_combine(&(ctrl->bus_head));
1352
1353 if (is_bridge(func)) { 632 if (is_bridge(func)) {
1354 dbg("PCI Bridge Hot-Remove s:b:d:f(%02x:%02x:%02x:%02x)\n", 633 dbg("PCI Bridge Hot-Remove s:b:d:f(%02x:%02x:%02x:%02x)\n",
1355 ctrl->seg, func->bus, func->device, func->function); 634 ctrl->seg, func->bus, func->device, func->function);
@@ -1918,787 +1197,3 @@ int pciehp_disable_slot(struct slot *p_slot)
1918 return rc; 1197 return rc;
1919} 1198}
1920 1199
1921
1922/**
1923 * configure_new_device - Configures the PCI header information of one board.
1924 *
1925 * @ctrl: pointer to controller structure
1926 * @func: pointer to function structure
1927 * @behind_bridge: 1 if this is a recursive call, 0 if not
1928 * @resources: pointer to set of resource lists
1929 *
1930 * Returns 0 if success
1931 *
1932 */
1933static u32 configure_new_device(struct controller * ctrl, struct pci_func * func,
1934 u8 behind_bridge, struct resource_lists * resources, u8 bridge_bus, u8 bridge_dev)
1935{
1936 u8 temp_byte, function, max_functions, stop_it;
1937 int rc;
1938 u32 ID;
1939 struct pci_func *new_slot;
1940 struct pci_bus lpci_bus, *pci_bus;
1941 int index;
1942
1943 new_slot = func;
1944
1945 dbg("%s\n", __FUNCTION__);
1946 memcpy(&lpci_bus, ctrl->pci_dev->subordinate, sizeof(lpci_bus));
1947 pci_bus = &lpci_bus;
1948 pci_bus->number = func->bus;
1949
1950 /* Check for Multi-function device */
1951 rc = pci_bus_read_config_byte(pci_bus, PCI_DEVFN(func->device, func->function), 0x0E, &temp_byte);
1952 if (rc) {
1953 dbg("%s: rc = %d\n", __FUNCTION__, rc);
1954 return rc;
1955 }
1956
1957 if (temp_byte & 0x80) /* Multi-function device */
1958 max_functions = 8;
1959 else
1960 max_functions = 1;
1961
1962 function = 0;
1963
1964 do {
1965 rc = configure_new_function(ctrl, new_slot, behind_bridge,
1966 resources, bridge_bus, bridge_dev);
1967
1968 if (rc) {
1969 dbg("configure_new_function failed: %d\n", rc);
1970 index = 0;
1971
1972 while (new_slot) {
1973 new_slot = pciehp_slot_find(new_slot->bus,
1974 new_slot->device, index++);
1975
1976 if (new_slot)
1977 pciehp_return_board_resources(new_slot,
1978 resources);
1979 }
1980
1981 return rc;
1982 }
1983
1984 function++;
1985
1986 stop_it = 0;
1987
1988 /* The following loop skips to the next present function
1989 * and creates a board structure
1990 */
1991
1992 while ((function < max_functions) && (!stop_it)) {
1993 pci_bus_read_config_dword(pci_bus, PCI_DEVFN(func->device, function), 0x00, &ID);
1994
1995 if (ID == 0xFFFFFFFF) { /* There's nothing there. */
1996 function++;
1997 } else { /* There's something there */
1998 /* Setup slot structure. */
1999 new_slot = pciehp_slot_create(func->bus);
2000
2001 if (new_slot == NULL) {
2002 /* Out of memory */
2003 return 1;
2004 }
2005
2006 new_slot->bus = func->bus;
2007 new_slot->device = func->device;
2008 new_slot->function = function;
2009 new_slot->is_a_board = 1;
2010 new_slot->status = 0;
2011
2012 stop_it++;
2013 }
2014 }
2015
2016 } while (function < max_functions);
2017 dbg("returning from %s\n", __FUNCTION__);
2018
2019 return 0;
2020}
2021
2022/*
2023 * Configuration logic that involves the hotplug data structures and
2024 * their bookkeeping
2025 */
2026
2027/**
2028 * configure_bridge: fill bridge's registers, either configure or disable it.
2029 */
2030static int
2031configure_bridge(struct pci_bus *pci_bus, unsigned int devfn,
2032 struct pci_resource *mem_node,
2033 struct pci_resource **hold_mem_node,
2034 int base_addr, int limit_addr)
2035{
2036 u16 temp_word;
2037 u32 rc;
2038
2039 if (mem_node) {
2040 memcpy(*hold_mem_node, mem_node, sizeof(struct pci_resource));
2041 mem_node->next = NULL;
2042
2043 /* set Mem base and Limit registers */
2044 RES_CHECK(mem_node->base, 16);
2045 temp_word = (u16)(mem_node->base >> 16);
2046 rc = pci_bus_write_config_word(pci_bus, devfn, base_addr, temp_word);
2047
2048 RES_CHECK(mem_node->base + mem_node->length - 1, 16);
2049 temp_word = (u16)((mem_node->base + mem_node->length - 1) >> 16);
2050 rc = pci_bus_write_config_word(pci_bus, devfn, limit_addr, temp_word);
2051 } else {
2052 temp_word = 0xFFFF;
2053 rc = pci_bus_write_config_word(pci_bus, devfn, base_addr, temp_word);
2054
2055 temp_word = 0x0000;
2056 rc = pci_bus_write_config_word(pci_bus, devfn, limit_addr, temp_word);
2057
2058 kfree(*hold_mem_node);
2059 *hold_mem_node = NULL;
2060 }
2061 return rc;
2062}
2063
2064static int
2065configure_new_bridge(struct controller *ctrl, struct pci_func *func,
2066 u8 behind_bridge, struct resource_lists *resources,
2067 struct pci_bus *pci_bus)
2068{
2069 int cloop;
2070 u8 temp_byte;
2071 u8 device;
2072 u16 temp_word;
2073 u32 rc;
2074 u32 ID;
2075 unsigned int devfn;
2076 struct pci_resource *mem_node;
2077 struct pci_resource *p_mem_node;
2078 struct pci_resource *io_node;
2079 struct pci_resource *bus_node;
2080 struct pci_resource *hold_mem_node;
2081 struct pci_resource *hold_p_mem_node;
2082 struct pci_resource *hold_IO_node;
2083 struct pci_resource *hold_bus_node;
2084 struct irq_mapping irqs;
2085 struct pci_func *new_slot;
2086 struct resource_lists temp_resources;
2087
2088 devfn = PCI_DEVFN(func->device, func->function);
2089
2090 /* set Primary bus */
2091 dbg("set Primary bus = 0x%x\n", func->bus);
2092 rc = pci_bus_write_config_byte(pci_bus, devfn, PCI_PRIMARY_BUS, func->bus);
2093 if (rc)
2094 return rc;
2095
2096 /* find range of busses to use */
2097 bus_node = get_max_resource(&resources->bus_head, 1L);
2098
2099 /* If we don't have any busses to allocate, we can't continue */
2100 if (!bus_node) {
2101 err("Got NO bus resource to use\n");
2102 return -ENOMEM;
2103 }
2104 dbg("Got ranges of buses to use: base:len=0x%x:%x\n", bus_node->base, bus_node->length);
2105
2106 /* set Secondary bus */
2107 temp_byte = (u8)bus_node->base;
2108 dbg("set Secondary bus = 0x%x\n", temp_byte);
2109 rc = pci_bus_write_config_byte(pci_bus, devfn, PCI_SECONDARY_BUS, temp_byte);
2110 if (rc)
2111 return rc;
2112
2113 /* set subordinate bus */
2114 temp_byte = (u8)(bus_node->base + bus_node->length - 1);
2115 dbg("set subordinate bus = 0x%x\n", temp_byte);
2116 rc = pci_bus_write_config_byte (pci_bus, devfn, PCI_SUBORDINATE_BUS, temp_byte);
2117 if (rc)
2118 return rc;
2119
2120 /* Set HP parameters (Cache Line Size, Latency Timer) */
2121 rc = pciehprm_set_hpp(ctrl, func, PCI_HEADER_TYPE_BRIDGE);
2122 if (rc)
2123 return rc;
2124
2125 /* Setup the IO, memory, and prefetchable windows */
2126
2127 io_node = get_max_resource(&(resources->io_head), 0x1000L);
2128 if (io_node) {
2129 dbg("io_node(base, len, next) (%x, %x, %p)\n", io_node->base,
2130 io_node->length, io_node->next);
2131 }
2132
2133 mem_node = get_max_resource(&(resources->mem_head), 0x100000L);
2134 if (mem_node) {
2135 dbg("mem_node(base, len, next) (%x, %x, %p)\n", mem_node->base,
2136 mem_node->length, mem_node->next);
2137 }
2138
2139 if (resources->p_mem_head)
2140 p_mem_node = get_max_resource(&(resources->p_mem_head), 0x100000L);
2141 else {
2142 /*
2143 * In some platform implementation, MEM and PMEM are not
2144 * distinguished, and hence ACPI _CRS has only MEM entries
2145 * for both MEM and PMEM.
2146 */
2147 dbg("using MEM for PMEM\n");
2148 p_mem_node = get_max_resource(&(resources->mem_head), 0x100000L);
2149 }
2150 if (p_mem_node) {
2151 dbg("p_mem_node(base, len, next) (%x, %x, %p)\n", p_mem_node->base,
2152 p_mem_node->length, p_mem_node->next);
2153 }
2154
2155 /* set up the IRQ info */
2156 if (!resources->irqs) {
2157 irqs.barber_pole = 0;
2158 irqs.interrupt[0] = 0;
2159 irqs.interrupt[1] = 0;
2160 irqs.interrupt[2] = 0;
2161 irqs.interrupt[3] = 0;
2162 irqs.valid_INT = 0;
2163 } else {
2164 irqs.barber_pole = resources->irqs->barber_pole;
2165 irqs.interrupt[0] = resources->irqs->interrupt[0];
2166 irqs.interrupt[1] = resources->irqs->interrupt[1];
2167 irqs.interrupt[2] = resources->irqs->interrupt[2];
2168 irqs.interrupt[3] = resources->irqs->interrupt[3];
2169 irqs.valid_INT = resources->irqs->valid_INT;
2170 }
2171
2172 /* set up resource lists that are now aligned on top and bottom
2173 * for anything behind the bridge.
2174 */
2175 temp_resources.bus_head = bus_node;
2176 temp_resources.io_head = io_node;
2177 temp_resources.mem_head = mem_node;
2178 temp_resources.p_mem_head = p_mem_node;
2179 temp_resources.irqs = &irqs;
2180
2181 /* Make copies of the nodes we are going to pass down so that
2182 * if there is a problem,we can just use these to free resources
2183 */
2184 hold_bus_node = kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
2185 hold_IO_node = kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
2186 hold_mem_node = kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
2187 hold_p_mem_node = kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
2188
2189 if (!hold_bus_node || !hold_IO_node || !hold_mem_node || !hold_p_mem_node) {
2190 kfree(hold_bus_node);
2191 kfree(hold_IO_node);
2192 kfree(hold_mem_node);
2193 kfree(hold_p_mem_node);
2194
2195 return 1;
2196 }
2197
2198 memcpy(hold_bus_node, bus_node, sizeof(struct pci_resource));
2199
2200 bus_node->base += 1;
2201 bus_node->length -= 1;
2202 bus_node->next = NULL;
2203
2204 /* If we have IO resources copy them and fill in the bridge's
2205 * IO range registers
2206 */
2207 if (io_node) {
2208 memcpy(hold_IO_node, io_node, sizeof(struct pci_resource));
2209 io_node->next = NULL;
2210
2211 /* set IO base and Limit registers */
2212 RES_CHECK(io_node->base, 8);
2213 temp_byte = (u8)(io_node->base >> 8);
2214 rc = pci_bus_write_config_byte (pci_bus, devfn, PCI_IO_BASE, temp_byte);
2215
2216 RES_CHECK(io_node->base + io_node->length - 1, 8);
2217 temp_byte = (u8)((io_node->base + io_node->length - 1) >> 8);
2218 rc = pci_bus_write_config_byte (pci_bus, devfn, PCI_IO_LIMIT, temp_byte);
2219 } else {
2220 kfree(hold_IO_node);
2221 hold_IO_node = NULL;
2222 }
2223
2224 /* If we have memory resources copy them and fill in the bridge's
2225 * memory range registers. Otherwise, fill in the range
2226 * registers with values that disable them.
2227 */
2228 rc = configure_bridge(pci_bus, devfn, mem_node, &hold_mem_node,
2229 PCI_MEMORY_BASE, PCI_MEMORY_LIMIT);
2230
2231 /* If we have prefetchable memory resources copy them and
2232 * fill in the bridge's memory range registers. Otherwise,
2233 * fill in the range registers with values that disable them.
2234 */
2235 rc = configure_bridge(pci_bus, devfn, p_mem_node, &hold_p_mem_node,
2236 PCI_PREF_MEMORY_BASE, PCI_PREF_MEMORY_LIMIT);
2237
2238 /* Adjust this to compensate for extra adjustment in first loop */
2239 irqs.barber_pole--;
2240
2241 rc = 0;
2242
2243 /* Here we actually find the devices and configure them */
2244 for (device = 0; (device <= 0x1F) && !rc; device++) {
2245 irqs.barber_pole = (irqs.barber_pole + 1) & 0x03;
2246
2247 ID = 0xFFFFFFFF;
2248 pci_bus->number = hold_bus_node->base;
2249 pci_bus_read_config_dword (pci_bus, PCI_DEVFN(device, 0), PCI_VENDOR_ID, &ID);
2250 pci_bus->number = func->bus;
2251
2252 if (ID != 0xFFFFFFFF) { /* device Present */
2253 /* Setup slot structure. */
2254 new_slot = pciehp_slot_create(hold_bus_node->base);
2255
2256 if (new_slot == NULL) {
2257 /* Out of memory */
2258 rc = -ENOMEM;
2259 continue;
2260 }
2261
2262 new_slot->bus = hold_bus_node->base;
2263 new_slot->device = device;
2264 new_slot->function = 0;
2265 new_slot->is_a_board = 1;
2266 new_slot->status = 0;
2267
2268 rc = configure_new_device(ctrl, new_slot, 1,
2269 &temp_resources, func->bus,
2270 func->device);
2271 dbg("configure_new_device rc=0x%x\n",rc);
2272 } /* End of IF (device in slot?) */
2273 } /* End of FOR loop */
2274
2275 if (rc) {
2276 pciehp_destroy_resource_list(&temp_resources);
2277
2278 return_resource(&(resources->bus_head), hold_bus_node);
2279 return_resource(&(resources->io_head), hold_IO_node);
2280 return_resource(&(resources->mem_head), hold_mem_node);
2281 return_resource(&(resources->p_mem_head), hold_p_mem_node);
2282 return(rc);
2283 }
2284
2285 /* save the interrupt routing information */
2286 if (resources->irqs) {
2287 resources->irqs->interrupt[0] = irqs.interrupt[0];
2288 resources->irqs->interrupt[1] = irqs.interrupt[1];
2289 resources->irqs->interrupt[2] = irqs.interrupt[2];
2290 resources->irqs->interrupt[3] = irqs.interrupt[3];
2291 resources->irqs->valid_INT = irqs.valid_INT;
2292 } else if (!behind_bridge) {
2293 /* We need to hook up the interrupts here */
2294 for (cloop = 0; cloop < 4; cloop++) {
2295 if (irqs.valid_INT & (0x01 << cloop)) {
2296 rc = pciehp_set_irq(func->bus, func->device,
2297 0x0A + cloop, irqs.interrupt[cloop]);
2298 if (rc) {
2299 pciehp_destroy_resource_list (&temp_resources);
2300 return_resource(&(resources->bus_head), hold_bus_node);
2301 return_resource(&(resources->io_head), hold_IO_node);
2302 return_resource(&(resources->mem_head), hold_mem_node);
2303 return_resource(&(resources->p_mem_head), hold_p_mem_node);
2304 return rc;
2305 }
2306 }
2307 } /* end of for loop */
2308 }
2309
2310 /* Return unused bus resources
2311 * First use the temporary node to store information for the board
2312 */
2313 if (hold_bus_node && bus_node && temp_resources.bus_head) {
2314 hold_bus_node->length = bus_node->base - hold_bus_node->base;
2315
2316 hold_bus_node->next = func->bus_head;
2317 func->bus_head = hold_bus_node;
2318
2319 temp_byte = (u8)(temp_resources.bus_head->base - 1);
2320
2321 /* set subordinate bus */
2322 dbg("re-set subordinate bus = 0x%x\n", temp_byte);
2323 rc = pci_bus_write_config_byte (pci_bus, devfn, PCI_SUBORDINATE_BUS, temp_byte);
2324
2325 if (temp_resources.bus_head->length == 0) {
2326 kfree(temp_resources.bus_head);
2327 temp_resources.bus_head = NULL;
2328 } else {
2329 dbg("return bus res of b:d(0x%x:%x) base:len(0x%x:%x)\n",
2330 func->bus, func->device, temp_resources.bus_head->base, temp_resources.bus_head->length);
2331 return_resource(&(resources->bus_head), temp_resources.bus_head);
2332 }
2333 }
2334
2335 /* If we have IO space available and there is some left,
2336 * return the unused portion
2337 */
2338 if (hold_IO_node && temp_resources.io_head) {
2339 io_node = do_pre_bridge_resource_split(&(temp_resources.io_head),
2340 &hold_IO_node, 0x1000);
2341
2342 /* Check if we were able to split something off */
2343 if (io_node) {
2344 hold_IO_node->base = io_node->base + io_node->length;
2345
2346 RES_CHECK(hold_IO_node->base, 8);
2347 temp_byte = (u8)((hold_IO_node->base) >> 8);
2348 rc = pci_bus_write_config_byte (pci_bus, devfn, PCI_IO_BASE, temp_byte);
2349
2350 return_resource(&(resources->io_head), io_node);
2351 }
2352
2353 io_node = do_bridge_resource_split(&(temp_resources.io_head), 0x1000);
2354
2355 /* Check if we were able to split something off */
2356 if (io_node) {
2357 /* First use the temporary node to store information for the board */
2358 hold_IO_node->length = io_node->base - hold_IO_node->base;
2359
2360 /* If we used any, add it to the board's list */
2361 if (hold_IO_node->length) {
2362 hold_IO_node->next = func->io_head;
2363 func->io_head = hold_IO_node;
2364
2365 RES_CHECK(io_node->base - 1, 8);
2366 temp_byte = (u8)((io_node->base - 1) >> 8);
2367 rc = pci_bus_write_config_byte (pci_bus, devfn, PCI_IO_LIMIT, temp_byte);
2368
2369 return_resource(&(resources->io_head), io_node);
2370 } else {
2371 /* it doesn't need any IO */
2372 temp_byte = 0x00;
2373 rc = pci_bus_write_config_byte(pci_bus, devfn, PCI_IO_LIMIT, temp_byte);
2374
2375 return_resource(&(resources->io_head), io_node);
2376 kfree(hold_IO_node);
2377 }
2378 } else {
2379 /* it used most of the range */
2380 hold_IO_node->next = func->io_head;
2381 func->io_head = hold_IO_node;
2382 }
2383 } else if (hold_IO_node) {
2384 /* it used the whole range */
2385 hold_IO_node->next = func->io_head;
2386 func->io_head = hold_IO_node;
2387 }
2388
2389 /* If we have memory space available and there is some left,
2390 * return the unused portion
2391 */
2392 if (hold_mem_node && temp_resources.mem_head) {
2393 mem_node = do_pre_bridge_resource_split(&(temp_resources.mem_head), &hold_mem_node, 0x100000L);
2394
2395 /* Check if we were able to split something off */
2396 if (mem_node) {
2397 hold_mem_node->base = mem_node->base + mem_node->length;
2398
2399 RES_CHECK(hold_mem_node->base, 16);
2400 temp_word = (u16)((hold_mem_node->base) >> 16);
2401 rc = pci_bus_write_config_word (pci_bus, devfn, PCI_MEMORY_BASE, temp_word);
2402
2403 return_resource(&(resources->mem_head), mem_node);
2404 }
2405
2406 mem_node = do_bridge_resource_split(&(temp_resources.mem_head), 0x100000L);
2407
2408 /* Check if we were able to split something off */
2409 if (mem_node) {
2410 /* First use the temporary node to store information for the board */
2411 hold_mem_node->length = mem_node->base - hold_mem_node->base;
2412
2413 if (hold_mem_node->length) {
2414 hold_mem_node->next = func->mem_head;
2415 func->mem_head = hold_mem_node;
2416
2417 /* configure end address */
2418 RES_CHECK(mem_node->base - 1, 16);
2419 temp_word = (u16)((mem_node->base - 1) >> 16);
2420 rc = pci_bus_write_config_word (pci_bus, devfn, PCI_MEMORY_LIMIT, temp_word);
2421
2422 /* Return unused resources to the pool */
2423 return_resource(&(resources->mem_head), mem_node);
2424 } else {
2425 /* it doesn't need any Mem */
2426 temp_word = 0x0000;
2427 rc = pci_bus_write_config_word (pci_bus, devfn, PCI_MEMORY_LIMIT, temp_word);
2428
2429 return_resource(&(resources->mem_head), mem_node);
2430 kfree(hold_mem_node);
2431 }
2432 } else {
2433 /* it used most of the range */
2434 hold_mem_node->next = func->mem_head;
2435 func->mem_head = hold_mem_node;
2436 }
2437 } else if (hold_mem_node) {
2438 /* it used the whole range */
2439 hold_mem_node->next = func->mem_head;
2440 func->mem_head = hold_mem_node;
2441 }
2442
2443 /* If we have prefetchable memory space available and there is some
2444 * left at the end, return the unused portion
2445 */
2446 if (hold_p_mem_node && temp_resources.p_mem_head) {
2447 p_mem_node = do_pre_bridge_resource_split(&(temp_resources.p_mem_head),
2448 &hold_p_mem_node, 0x100000L);
2449
2450 /* Check if we were able to split something off */
2451 if (p_mem_node) {
2452 hold_p_mem_node->base = p_mem_node->base + p_mem_node->length;
2453
2454 RES_CHECK(hold_p_mem_node->base, 16);
2455 temp_word = (u16)((hold_p_mem_node->base) >> 16);
2456 rc = pci_bus_write_config_word (pci_bus, devfn, PCI_PREF_MEMORY_BASE, temp_word);
2457
2458 return_resource(&(resources->p_mem_head), p_mem_node);
2459 }
2460
2461 p_mem_node = do_bridge_resource_split(&(temp_resources.p_mem_head), 0x100000L);
2462
2463 /* Check if we were able to split something off */
2464 if (p_mem_node) {
2465 /* First use the temporary node to store information for the board */
2466 hold_p_mem_node->length = p_mem_node->base - hold_p_mem_node->base;
2467
2468 /* If we used any, add it to the board's list */
2469 if (hold_p_mem_node->length) {
2470 hold_p_mem_node->next = func->p_mem_head;
2471 func->p_mem_head = hold_p_mem_node;
2472
2473 RES_CHECK(p_mem_node->base - 1, 16);
2474 temp_word = (u16)((p_mem_node->base - 1) >> 16);
2475 rc = pci_bus_write_config_word (pci_bus, devfn, PCI_PREF_MEMORY_LIMIT, temp_word);
2476
2477 return_resource(&(resources->p_mem_head), p_mem_node);
2478 } else {
2479 /* it doesn't need any PMem */
2480 temp_word = 0x0000;
2481 rc = pci_bus_write_config_word (pci_bus, devfn, PCI_PREF_MEMORY_LIMIT, temp_word);
2482
2483 return_resource(&(resources->p_mem_head), p_mem_node);
2484 kfree(hold_p_mem_node);
2485 }
2486 } else {
2487 /* it used the most of the range */
2488 hold_p_mem_node->next = func->p_mem_head;
2489 func->p_mem_head = hold_p_mem_node;
2490 }
2491 } else if (hold_p_mem_node) {
2492 /* it used the whole range */
2493 hold_p_mem_node->next = func->p_mem_head;
2494 func->p_mem_head = hold_p_mem_node;
2495 }
2496
2497 /* We should be configuring an IRQ and the bridge's base address
2498 * registers if it needs them. Although we have never seen such
2499 * a device
2500 */
2501
2502 pciehprm_enable_card(ctrl, func, PCI_HEADER_TYPE_BRIDGE);
2503
2504 dbg("PCI Bridge Hot-Added s:b:d:f(%02x:%02x:%02x:%02x)\n", ctrl->seg, func->bus, func->device, func->function);
2505
2506 return rc;
2507}
2508
2509/**
2510 * configure_new_function - Configures the PCI header information of one device
2511 *
2512 * @ctrl: pointer to controller structure
2513 * @func: pointer to function structure
2514 * @behind_bridge: 1 if this is a recursive call, 0 if not
2515 * @resources: pointer to set of resource lists
2516 *
2517 * Calls itself recursively for bridged devices.
2518 * Returns 0 if success
2519 *
2520 */
2521static int
2522configure_new_function(struct controller *ctrl, struct pci_func *func,
2523 u8 behind_bridge, struct resource_lists *resources,
2524 u8 bridge_bus, u8 bridge_dev)
2525{
2526 int cloop;
2527 u8 temp_byte;
2528 u8 class_code;
2529 u32 rc;
2530 u32 temp_register;
2531 u32 base;
2532 unsigned int devfn;
2533 struct pci_resource *mem_node;
2534 struct pci_resource *io_node;
2535 struct pci_bus lpci_bus, *pci_bus;
2536
2537 memcpy(&lpci_bus, ctrl->pci_dev->subordinate, sizeof(lpci_bus));
2538 pci_bus = &lpci_bus;
2539 pci_bus->number = func->bus;
2540 devfn = PCI_DEVFN(func->device, func->function);
2541
2542 /* Check for Bridge */
2543 rc = pci_bus_read_config_byte(pci_bus, devfn, PCI_HEADER_TYPE, &temp_byte);
2544 if (rc)
2545 return rc;
2546 dbg("%s: bus %x dev %x func %x temp_byte = %x\n", __FUNCTION__,
2547 func->bus, func->device, func->function, temp_byte);
2548
2549 if ((temp_byte & 0x7F) == PCI_HEADER_TYPE_BRIDGE) { /* PCI-PCI Bridge */
2550 rc = configure_new_bridge(ctrl, func, behind_bridge, resources,
2551 pci_bus);
2552
2553 if (rc)
2554 return rc;
2555 } else if ((temp_byte & 0x7F) == PCI_HEADER_TYPE_NORMAL) {
2556 /* Standard device */
2557 u64 base64;
2558 rc = pci_bus_read_config_byte(pci_bus, devfn, 0x0B, &class_code);
2559
2560 if (class_code == PCI_BASE_CLASS_DISPLAY)
2561 return DEVICE_TYPE_NOT_SUPPORTED;
2562
2563 /* Figure out IO and memory needs */
2564 for (cloop = PCI_BASE_ADDRESS_0; cloop <= PCI_BASE_ADDRESS_5; cloop += 4) {
2565 temp_register = 0xFFFFFFFF;
2566
2567 rc = pci_bus_write_config_dword (pci_bus, devfn, cloop, temp_register);
2568 rc = pci_bus_read_config_dword(pci_bus, devfn, cloop, &temp_register);
2569 dbg("Bar[%x]=0x%x on bus:dev:func(0x%x:%x:%x)\n", cloop, temp_register,
2570 func->bus, func->device, func->function);
2571
2572 if (!temp_register)
2573 continue;
2574
2575 base64 = 0L;
2576 if (temp_register & PCI_BASE_ADDRESS_SPACE_IO) {
2577 /* Map IO */
2578
2579 /* set base = amount of IO space */
2580 base = temp_register & 0xFFFFFFFC;
2581 base = ~base + 1;
2582
2583 dbg("NEED IO length(0x%x)\n", base);
2584 io_node = get_io_resource(&(resources->io_head),(ulong)base);
2585
2586 /* allocate the resource to the board */
2587 if (io_node) {
2588 dbg("Got IO base=0x%x(length=0x%x)\n", io_node->base, io_node->length);
2589 base = (u32)io_node->base;
2590 io_node->next = func->io_head;
2591 func->io_head = io_node;
2592 } else {
2593 err("Got NO IO resource(length=0x%x)\n", base);
2594 return -ENOMEM;
2595 }
2596 } else { /* map MEM */
2597 int prefetchable = 1;
2598 struct pci_resource **res_node = &func->p_mem_head;
2599 char *res_type_str = "PMEM";
2600 u32 temp_register2;
2601
2602 if (!(temp_register & PCI_BASE_ADDRESS_MEM_PREFETCH)) {
2603 prefetchable = 0;
2604 res_node = &func->mem_head;
2605 res_type_str++;
2606 }
2607
2608 base = temp_register & 0xFFFFFFF0;
2609 base = ~base + 1;
2610
2611 switch (temp_register & PCI_BASE_ADDRESS_MEM_TYPE_MASK) {
2612 case PCI_BASE_ADDRESS_MEM_TYPE_32:
2613 dbg("NEED 32 %s bar=0x%x(length=0x%x)\n", res_type_str, temp_register, base);
2614
2615 if (prefetchable && resources->p_mem_head)
2616 mem_node=get_resource(&(resources->p_mem_head), (ulong)base);
2617 else {
2618 if (prefetchable)
2619 dbg("using MEM for PMEM\n");
2620 mem_node = get_resource(&(resources->mem_head), (ulong)base);
2621 }
2622
2623 /* allocate the resource to the board */
2624 if (mem_node) {
2625 base = (u32)mem_node->base;
2626 mem_node->next = *res_node;
2627 *res_node = mem_node;
2628 dbg("Got 32 %s base=0x%x(length=0x%x)\n", res_type_str, mem_node->base,
2629 mem_node->length);
2630 } else {
2631 err("Got NO 32 %s resource(length=0x%x)\n", res_type_str, base);
2632 return -ENOMEM;
2633 }
2634 break;
2635 case PCI_BASE_ADDRESS_MEM_TYPE_64:
2636 rc = pci_bus_read_config_dword(pci_bus, devfn, cloop+4, &temp_register2);
2637 dbg("NEED 64 %s bar=0x%x:%x(length=0x%x)\n", res_type_str, temp_register2,
2638 temp_register, base);
2639
2640 if (prefetchable && resources->p_mem_head)
2641 mem_node = get_resource(&(resources->p_mem_head), (ulong)base);
2642 else {
2643 if (prefetchable)
2644 dbg("using MEM for PMEM\n");
2645 mem_node = get_resource(&(resources->mem_head), (ulong)base);
2646 }
2647
2648 /* allocate the resource to the board */
2649 if (mem_node) {
2650 base64 = mem_node->base;
2651 mem_node->next = *res_node;
2652 *res_node = mem_node;
2653 dbg("Got 64 %s base=0x%x:%x(length=%x)\n", res_type_str, (u32)(base64 >> 32),
2654 (u32)base64, mem_node->length);
2655 } else {
2656 err("Got NO 64 %s resource(length=0x%x)\n", res_type_str, base);
2657 return -ENOMEM;
2658 }
2659 break;
2660 default:
2661 dbg("reserved BAR type=0x%x\n", temp_register);
2662 break;
2663 }
2664
2665 }
2666
2667 if (base64) {
2668 rc = pci_bus_write_config_dword(pci_bus, devfn, cloop, (u32)base64);
2669 cloop += 4;
2670 base64 >>= 32;
2671
2672 if (base64) {
2673 dbg("%s: high dword of base64(0x%x) set to 0\n", __FUNCTION__, (u32)base64);
2674 base64 = 0x0L;
2675 }
2676
2677 rc = pci_bus_write_config_dword(pci_bus, devfn, cloop, (u32)base64);
2678 } else {
2679 rc = pci_bus_write_config_dword(pci_bus, devfn, cloop, base);
2680 }
2681 } /* End of base register loop */
2682
2683 /* disable ROM base Address */
2684 rc = pci_bus_write_config_dword (pci_bus, devfn, PCI_ROM_ADDRESS, 0x00);
2685
2686 /* Set HP parameters (Cache Line Size, Latency Timer) */
2687 rc = pciehprm_set_hpp(ctrl, func, PCI_HEADER_TYPE_NORMAL);
2688 if (rc)
2689 return rc;
2690
2691 pciehprm_enable_card(ctrl, func, PCI_HEADER_TYPE_NORMAL);
2692
2693 dbg("PCI function Hot-Added s:b:d:f(%02x:%02x:%02x:%02x)\n", ctrl->seg, func->bus, func->device,
2694 func->function);
2695 } /* End of Not-A-Bridge else */
2696 else {
2697 /* It's some strange type of PCI adapter (Cardbus?) */
2698 return DEVICE_TYPE_NOT_SUPPORTED;
2699 }
2700
2701 func->configured = 1;
2702
2703 return 0;
2704}
diff --git a/drivers/pci/hotplug/pciehp_pci.c b/drivers/pci/hotplug/pciehp_pci.c
index ff17d8e07e94..db59a06ab0b4 100644
--- a/drivers/pci/hotplug/pciehp_pci.c
+++ b/drivers/pci/hotplug/pciehp_pci.c
@@ -37,47 +37,70 @@
37#include <linux/pci.h> 37#include <linux/pci.h>
38#include "../pci.h" 38#include "../pci.h"
39#include "pciehp.h" 39#include "pciehp.h"
40#ifndef CONFIG_IA64
41#include "../../../arch/i386/pci/pci.h" /* horrible hack showing how processor dependant we are... */
42#endif
43 40
44 41
45int pciehp_configure_device (struct controller* ctrl, struct pci_func* func) 42int pciehp_configure_device(struct slot *p_slot)
46{ 43{
47 unsigned char bus; 44 struct pci_dev *dev;
48 struct pci_bus *child; 45 struct pci_bus *parent = p_slot->ctrl->pci_dev->subordinate;
49 int num; 46 int num, fn;
50 47
51 if (func->pci_dev == NULL) 48 dev = pci_find_slot(p_slot->bus, PCI_DEVFN(p_slot->device, 0));
52 func->pci_dev = pci_find_slot(func->bus, PCI_DEVFN(func->device, func->function)); 49 if (dev) {
53 50 err("Device %s already exists at %x:%x, cannot hot-add\n",
54 /* Still NULL ? Well then scan for it ! */ 51 pci_name(dev), p_slot->bus, p_slot->device);
55 if (func->pci_dev == NULL) { 52 return -EINVAL;
56 dbg("%s: pci_dev still null. do pci_scan_slot\n", __FUNCTION__);
57
58 num = pci_scan_slot(ctrl->pci_dev->subordinate, PCI_DEVFN(func->device, func->function));
59
60 if (num)
61 pci_bus_add_devices(ctrl->pci_dev->subordinate);
62
63 func->pci_dev = pci_find_slot(func->bus, PCI_DEVFN(func->device, func->function));
64 if (func->pci_dev == NULL) {
65 dbg("ERROR: pci_dev still null\n");
66 return 0;
67 }
68 } 53 }
69 54
70 if (func->pci_dev->hdr_type == PCI_HEADER_TYPE_BRIDGE) { 55 num = pci_scan_slot(parent, PCI_DEVFN(p_slot->device, 0));
71 pci_read_config_byte(func->pci_dev, PCI_SECONDARY_BUS, &bus); 56 if (num == 0) {
72 child = pci_add_new_bus(func->pci_dev->bus, (func->pci_dev), bus); 57 err("No new device found\n");
73 pci_do_scan_bus(child); 58 return -ENODEV;
59 }
74 60
61 for (fn = 0; fn < 8; fn++) {
62 if (!(dev = pci_find_slot(p_slot->bus,
63 PCI_DEVFN(p_slot->device, fn))))
64 continue;
65 if ((dev->class >> 16) == PCI_BASE_CLASS_DISPLAY) {
66 err("Cannot hot-add display device %s\n",
67 pci_name(dev));
68 continue;
69 }
70 if ((dev->hdr_type == PCI_HEADER_TYPE_BRIDGE) ||
71 (dev->hdr_type == PCI_HEADER_TYPE_CARDBUS)) {
72 /* Find an unused bus number for the new bridge */
73 struct pci_bus *child;
74 unsigned char busnr, start = parent->secondary;
75 unsigned char end = parent->subordinate;
76 for (busnr = start; busnr <= end; busnr++) {
77 if (!pci_find_bus(pci_domain_nr(parent),
78 busnr))
79 break;
80 }
81 if (busnr >= end) {
82 err("No free bus for hot-added bridge\n");
83 continue;
84 }
85 child = pci_add_new_bus(parent, dev, busnr);
86 if (!child) {
87 err("Cannot add new bus for %s\n",
88 pci_name(dev));
89 continue;
90 }
91 child->subordinate = pci_do_scan_bus(child);
92 pci_bus_size_bridges(child);
93 }
94 /* TBD: program firmware provided _HPP values */
95 /* program_fw_provided_values(dev); */
75 } 96 }
76 97
98 pci_bus_assign_resources(parent);
99 pci_bus_add_devices(parent);
100 pci_enable_bridges(parent);
77 return 0; 101 return 0;
78} 102}
79 103
80
81int pciehp_unconfigure_device(struct pci_func* func) 104int pciehp_unconfigure_device(struct pci_func* func)
82{ 105{
83 int rc = 0; 106 int rc = 0;
@@ -105,47 +128,6 @@ int pciehp_unconfigure_device(struct pci_func* func)
105} 128}
106 129
107/* 130/*
108 * pciehp_set_irq
109 *
110 * @bus_num: bus number of PCI device
111 * @dev_num: device number of PCI device
112 * @slot: pointer to u8 where slot number will be returned
113 */
114int pciehp_set_irq (u8 bus_num, u8 dev_num, u8 int_pin, u8 irq_num)
115{
116#if defined(CONFIG_X86_32) && !defined(CONFIG_X86_IO_APIC)
117 int rc;
118 u16 temp_word;
119 struct pci_dev fakedev;
120 struct pci_bus fakebus;
121
122 fakedev.devfn = dev_num << 3;
123 fakedev.bus = &fakebus;
124 fakebus.number = bus_num;
125 dbg("%s: dev %d, bus %d, pin %d, num %d\n",
126 __FUNCTION__, dev_num, bus_num, int_pin, irq_num);
127 rc = pcibios_set_irq_routing(&fakedev, int_pin - 0x0a, irq_num);
128 dbg("%s: rc %d\n", __FUNCTION__, rc);
129 if (!rc)
130 return !rc;
131
132 /* set the Edge Level Control Register (ELCR) */
133 temp_word = inb(0x4d0);
134 temp_word |= inb(0x4d1) << 8;
135
136 temp_word |= 0x01 << irq_num;
137
138 /* This should only be for x86 as it sets the Edge Level Control Register */
139 outb((u8) (temp_word & 0xFF), 0x4d0);
140 outb((u8) ((temp_word & 0xFF00) >> 8), 0x4d1);
141#endif
142 return 0;
143}
144
145/* More PCI configuration routines; this time centered around hotplug controller */
146
147
148/*
149 * pciehp_save_config 131 * pciehp_save_config
150 * 132 *
151 * Reads configuration for all slots in a PCI bus and saves info. 133 * Reads configuration for all slots in a PCI bus and saves info.
@@ -462,366 +444,3 @@ int pciehp_save_slot_config(struct controller *ctrl, struct pci_func * new_slot)
462 return 0; 444 return 0;
463} 445}
464 446
465
466/*
467 * pciehp_save_used_resources
468 *
469 * Stores used resource information for existing boards. this is
470 * for boards that were in the system when this driver was loaded.
471 * this function is for hot plug ADD
472 *
473 * returns 0 if success
474 * if disable == 1(DISABLE_CARD),
475 * it loops for all functions of the slot and disables them.
476 * else, it just get resources of the function and return.
477 */
478int pciehp_save_used_resources(struct controller *ctrl, struct pci_func *func, int disable)
479{
480 u8 cloop;
481 u8 header_type;
482 u8 secondary_bus;
483 u8 temp_byte;
484 u16 command;
485 u16 save_command;
486 u16 w_base, w_length;
487 u32 temp_register;
488 u32 save_base;
489 u32 base, length;
490 u64 base64 = 0;
491 int index = 0;
492 unsigned int devfn;
493 struct pci_resource *mem_node = NULL;
494 struct pci_resource *p_mem_node = NULL;
495 struct pci_resource *t_mem_node;
496 struct pci_resource *io_node;
497 struct pci_resource *bus_node;
498 struct pci_bus lpci_bus, *pci_bus;
499 memcpy(&lpci_bus, ctrl->pci_dev->subordinate, sizeof(lpci_bus));
500 pci_bus = &lpci_bus;
501
502 if (disable)
503 func = pciehp_slot_find(func->bus, func->device, index++);
504
505 while ((func != NULL) && func->is_a_board) {
506 pci_bus->number = func->bus;
507 devfn = PCI_DEVFN(func->device, func->function);
508
509 /* Save the command register */
510 pci_bus_read_config_word(pci_bus, devfn, PCI_COMMAND, &save_command);
511
512 if (disable) {
513 /* disable card */
514 command = 0x00;
515 pci_bus_write_config_word(pci_bus, devfn, PCI_COMMAND, command);
516 }
517
518 /* Check for Bridge */
519 pci_bus_read_config_byte(pci_bus, devfn, PCI_HEADER_TYPE, &header_type);
520
521 if ((header_type & 0x7F) == PCI_HEADER_TYPE_BRIDGE) { /* PCI-PCI Bridge */
522 dbg("Save_used_res of PCI bridge b:d=0x%x:%x, sc=0x%x\n",
523 func->bus, func->device, save_command);
524 if (disable) {
525 /* Clear Bridge Control Register */
526 command = 0x00;
527 pci_bus_write_config_word(pci_bus, devfn, PCI_BRIDGE_CONTROL, command);
528 }
529
530 pci_bus_read_config_byte(pci_bus, devfn, PCI_SECONDARY_BUS, &secondary_bus);
531 pci_bus_read_config_byte(pci_bus, devfn, PCI_SUBORDINATE_BUS, &temp_byte);
532
533 bus_node = kmalloc(sizeof(struct pci_resource),
534 GFP_KERNEL);
535 if (!bus_node)
536 return -ENOMEM;
537
538 bus_node->base = (ulong)secondary_bus;
539 bus_node->length = (ulong)(temp_byte - secondary_bus + 1);
540
541 bus_node->next = func->bus_head;
542 func->bus_head = bus_node;
543
544 /* Save IO base and Limit registers */
545 pci_bus_read_config_byte(pci_bus, devfn, PCI_IO_BASE, &temp_byte);
546 base = temp_byte;
547 pci_bus_read_config_byte(pci_bus, devfn, PCI_IO_LIMIT, &temp_byte);
548 length = temp_byte;
549
550 if ((base <= length) && (!disable || (save_command & PCI_COMMAND_IO))) {
551 io_node = kmalloc(sizeof(struct pci_resource),
552 GFP_KERNEL);
553 if (!io_node)
554 return -ENOMEM;
555
556 io_node->base = (ulong)(base & PCI_IO_RANGE_MASK) << 8;
557 io_node->length = (ulong)(length - base + 0x10) << 8;
558
559 io_node->next = func->io_head;
560 func->io_head = io_node;
561 }
562
563 /* Save memory base and Limit registers */
564 pci_bus_read_config_word(pci_bus, devfn, PCI_MEMORY_BASE, &w_base);
565 pci_bus_read_config_word(pci_bus, devfn, PCI_MEMORY_LIMIT, &w_length);
566
567 if ((w_base <= w_length) && (!disable || (save_command & PCI_COMMAND_MEMORY))) {
568 mem_node = kmalloc(sizeof(struct pci_resource),
569 GFP_KERNEL);
570 if (!mem_node)
571 return -ENOMEM;
572
573 mem_node->base = (ulong)w_base << 16;
574 mem_node->length = (ulong)(w_length - w_base + 0x10) << 16;
575
576 mem_node->next = func->mem_head;
577 func->mem_head = mem_node;
578 }
579 /* Save prefetchable memory base and Limit registers */
580 pci_bus_read_config_word(pci_bus, devfn, PCI_PREF_MEMORY_BASE, &w_base);
581 pci_bus_read_config_word(pci_bus, devfn, PCI_PREF_MEMORY_LIMIT, &w_length);
582
583 if ((w_base <= w_length) && (!disable || (save_command & PCI_COMMAND_MEMORY))) {
584 p_mem_node = kmalloc(sizeof(struct pci_resource),
585 GFP_KERNEL);
586 if (!p_mem_node)
587 return -ENOMEM;
588
589 p_mem_node->base = (ulong)w_base << 16;
590 p_mem_node->length = (ulong)(w_length - w_base + 0x10) << 16;
591
592 p_mem_node->next = func->p_mem_head;
593 func->p_mem_head = p_mem_node;
594 }
595 } else if ((header_type & 0x7F) == PCI_HEADER_TYPE_NORMAL) {
596 dbg("Save_used_res of PCI adapter b:d=0x%x:%x, sc=0x%x\n",
597 func->bus, func->device, save_command);
598
599 /* Figure out IO and memory base lengths */
600 for (cloop = PCI_BASE_ADDRESS_0; cloop <= PCI_BASE_ADDRESS_5; cloop += 4) {
601 pci_bus_read_config_dword(pci_bus, devfn, cloop, &save_base);
602
603 temp_register = 0xFFFFFFFF;
604 pci_bus_write_config_dword(pci_bus, devfn, cloop, temp_register);
605 pci_bus_read_config_dword(pci_bus, devfn, cloop, &temp_register);
606
607 if (!disable)
608 pci_bus_write_config_dword(pci_bus, devfn, cloop, save_base);
609
610 if (!temp_register)
611 continue;
612
613 base = temp_register;
614
615 if ((base & PCI_BASE_ADDRESS_SPACE_IO) &&
616 (!disable || (save_command & PCI_COMMAND_IO))) {
617 /* IO base */
618 /* set temp_register = amount of IO space requested */
619 base = base & 0xFFFFFFFCL;
620 base = (~base) + 1;
621
622 io_node = kmalloc(sizeof (struct pci_resource),
623 GFP_KERNEL);
624 if (!io_node)
625 return -ENOMEM;
626
627 io_node->base = (ulong)save_base & PCI_BASE_ADDRESS_IO_MASK;
628 io_node->length = (ulong)base;
629 dbg("sur adapter: IO bar=0x%x(length=0x%x)\n",
630 io_node->base, io_node->length);
631
632 io_node->next = func->io_head;
633 func->io_head = io_node;
634 } else { /* map Memory */
635 int prefetchable = 1;
636 /* struct pci_resources **res_node; */
637 char *res_type_str = "PMEM";
638 u32 temp_register2;
639
640 t_mem_node = kmalloc(sizeof (struct pci_resource),
641 GFP_KERNEL);
642 if (!t_mem_node)
643 return -ENOMEM;
644
645 if (!(base & PCI_BASE_ADDRESS_MEM_PREFETCH) &&
646 (!disable || (save_command & PCI_COMMAND_MEMORY))) {
647 prefetchable = 0;
648 mem_node = t_mem_node;
649 res_type_str++;
650 } else
651 p_mem_node = t_mem_node;
652
653 base = base & 0xFFFFFFF0L;
654 base = (~base) + 1;
655
656 switch (temp_register & PCI_BASE_ADDRESS_MEM_TYPE_MASK) {
657 case PCI_BASE_ADDRESS_MEM_TYPE_32:
658 if (prefetchable) {
659 p_mem_node->base = (ulong)save_base & PCI_BASE_ADDRESS_MEM_MASK;
660 p_mem_node->length = (ulong)base;
661 dbg("sur adapter: 32 %s bar=0x%x(length=0x%x)\n",
662 res_type_str,
663 p_mem_node->base,
664 p_mem_node->length);
665
666 p_mem_node->next = func->p_mem_head;
667 func->p_mem_head = p_mem_node;
668 } else {
669 mem_node->base = (ulong)save_base & PCI_BASE_ADDRESS_MEM_MASK;
670 mem_node->length = (ulong)base;
671 dbg("sur adapter: 32 %s bar=0x%x(length=0x%x)\n",
672 res_type_str,
673 mem_node->base,
674 mem_node->length);
675
676 mem_node->next = func->mem_head;
677 func->mem_head = mem_node;
678 }
679 break;
680 case PCI_BASE_ADDRESS_MEM_TYPE_64:
681 pci_bus_read_config_dword(pci_bus, devfn, cloop+4, &temp_register2);
682 base64 = temp_register2;
683 base64 = (base64 << 32) | save_base;
684
685 if (temp_register2) {
686 dbg("sur adapter: 64 %s high dword of base64(0x%x:%x) masked to 0\n",
687 res_type_str, temp_register2, (u32)base64);
688 base64 &= 0x00000000FFFFFFFFL;
689 }
690
691 if (prefetchable) {
692 p_mem_node->base = base64 & PCI_BASE_ADDRESS_MEM_MASK;
693 p_mem_node->length = base;
694 dbg("sur adapter: 64 %s base=0x%x(len=0x%x)\n",
695 res_type_str,
696 p_mem_node->base,
697 p_mem_node->length);
698
699 p_mem_node->next = func->p_mem_head;
700 func->p_mem_head = p_mem_node;
701 } else {
702 mem_node->base = base64 & PCI_BASE_ADDRESS_MEM_MASK;
703 mem_node->length = base;
704 dbg("sur adapter: 64 %s base=0x%x(len=0x%x)\n",
705 res_type_str,
706 mem_node->base,
707 mem_node->length);
708
709 mem_node->next = func->mem_head;
710 func->mem_head = mem_node;
711 }
712 cloop += 4;
713 break;
714 default:
715 dbg("asur: reserved BAR type=0x%x\n",
716 temp_register);
717 break;
718 }
719 }
720 } /* End of base register loop */
721 } else { /* Some other unknown header type */
722 dbg("Save_used_res of PCI unknown type b:d=0x%x:%x. skip.\n",
723 func->bus, func->device);
724 }
725
726 /* find the next device in this slot */
727 if (!disable)
728 break;
729 func = pciehp_slot_find(func->bus, func->device, index++);
730 }
731
732 return 0;
733}
734
735
736/**
737 * kfree_resource_list: release memory of all list members
738 * @res: resource list to free
739 */
740static inline void
741return_resource_list(struct pci_resource **func, struct pci_resource **res)
742{
743 struct pci_resource *node;
744 struct pci_resource *t_node;
745
746 node = *func;
747 *func = NULL;
748 while (node) {
749 t_node = node->next;
750 return_resource(res, node);
751 node = t_node;
752 }
753}
754
755/*
756 * pciehp_return_board_resources
757 *
758 * this routine returns all resources allocated to a board to
759 * the available pool.
760 *
761 * returns 0 if success
762 */
763int pciehp_return_board_resources(struct pci_func * func,
764 struct resource_lists * resources)
765{
766 int rc;
767
768 dbg("%s\n", __FUNCTION__);
769
770 if (!func)
771 return 1;
772
773 return_resource_list(&(func->io_head),&(resources->io_head));
774 return_resource_list(&(func->mem_head),&(resources->mem_head));
775 return_resource_list(&(func->p_mem_head),&(resources->p_mem_head));
776 return_resource_list(&(func->bus_head),&(resources->bus_head));
777
778 rc = pciehp_resource_sort_and_combine(&(resources->mem_head));
779 rc |= pciehp_resource_sort_and_combine(&(resources->p_mem_head));
780 rc |= pciehp_resource_sort_and_combine(&(resources->io_head));
781 rc |= pciehp_resource_sort_and_combine(&(resources->bus_head));
782
783 return rc;
784}
785
786/**
787 * kfree_resource_list: release memory of all list members
788 * @res: resource list to free
789 */
790static inline void
791kfree_resource_list(struct pci_resource **r)
792{
793 struct pci_resource *res, *tres;
794
795 res = *r;
796 *r = NULL;
797
798 while (res) {
799 tres = res;
800 res = res->next;
801 kfree(tres);
802 }
803}
804
805/**
806 * pciehp_destroy_resource_list: put node back in the resource list
807 * @resources: list to put nodes back
808 */
809void pciehp_destroy_resource_list(struct resource_lists * resources)
810{
811 kfree_resource_list(&(resources->io_head));
812 kfree_resource_list(&(resources->mem_head));
813 kfree_resource_list(&(resources->p_mem_head));
814 kfree_resource_list(&(resources->bus_head));
815}
816
817/**
818 * pciehp_destroy_board_resources: put node back in the resource list
819 * @resources: list to put nodes back
820 */
821void pciehp_destroy_board_resources(struct pci_func * func)
822{
823 kfree_resource_list(&(func->io_head));
824 kfree_resource_list(&(func->mem_head));
825 kfree_resource_list(&(func->p_mem_head));
826 kfree_resource_list(&(func->bus_head));
827}
diff --git a/drivers/pci/hotplug/pciehprm_acpi.c b/drivers/pci/hotplug/pciehprm_acpi.c
index 1406db35b089..078550ba2708 100644
--- a/drivers/pci/hotplug/pciehprm_acpi.c
+++ b/drivers/pci/hotplug/pciehprm_acpi.c
@@ -35,9 +35,6 @@
35#include <linux/pci-acpi.h> 35#include <linux/pci-acpi.h>
36#include <asm/uaccess.h> 36#include <asm/uaccess.h>
37#include <asm/system.h> 37#include <asm/system.h>
38#ifdef CONFIG_IA64
39#include <asm/iosapic.h>
40#endif
41#include <acpi/acpi.h> 38#include <acpi/acpi.h>
42#include <acpi/acpi_bus.h> 39#include <acpi/acpi_bus.h>
43#include <acpi/actypes.h> 40#include <acpi/actypes.h>
@@ -84,10 +81,6 @@ struct acpi_php_slot {
84 int dev; 81 int dev;
85 int fun; 82 int fun;
86 u32 sun; 83 u32 sun;
87 struct pci_resource *mem_head;
88 struct pci_resource *p_mem_head;
89 struct pci_resource *io_head;
90 struct pci_resource *bus_head;
91 void *slot_ops; /* _STA, _EJx, etc */ 84 void *slot_ops; /* _STA, _EJx, etc */
92 struct slot *slot; 85 struct slot *slot;
93}; /* per func */ 86}; /* per func */
@@ -104,14 +97,6 @@ struct acpi_bridge {
104 int bus; /* pdev->subordinate->number */ 97 int bus; /* pdev->subordinate->number */
105 struct acpi__hpp *_hpp; 98 struct acpi__hpp *_hpp;
106 struct acpi_php_slot *slots; 99 struct acpi_php_slot *slots;
107 struct pci_resource *tmem_head; /* total from crs */
108 struct pci_resource *tp_mem_head; /* total from crs */
109 struct pci_resource *tio_head; /* total from crs */
110 struct pci_resource *tbus_head; /* total from crs */
111 struct pci_resource *mem_head; /* available */
112 struct pci_resource *p_mem_head; /* available */
113 struct pci_resource *io_head; /* available */
114 struct pci_resource *bus_head; /* available */
115 int scanned; 100 int scanned;
116 int type; 101 int type;
117}; 102};
@@ -268,485 +253,6 @@ static int acpi_run_oshp ( struct acpi_bridge *ab)
268 return oshp_run_status; 253 return oshp_run_status;
269} 254}
270 255
271static acpi_status acpi_evaluate_crs(
272 acpi_handle handle,
273 struct acpi_resource **retbuf
274 )
275{
276 acpi_status status;
277 struct acpi_buffer crsbuf;
278 u8 *path_name = acpi_path_name(handle);
279
280 crsbuf.length = 0;
281 crsbuf.pointer = NULL;
282
283 status = acpi_get_current_resources (handle, &crsbuf);
284
285 switch (status) {
286 case AE_BUFFER_OVERFLOW:
287 break; /* found */
288 case AE_NOT_FOUND:
289 dbg("acpi_pciehprm:%s _CRS not found\n", path_name);
290 return status;
291 default:
292 err ("acpi_pciehprm:%s _CRS fail=0x%x\n", path_name, status);
293 return status;
294 }
295
296 crsbuf.pointer = kmalloc (crsbuf.length, GFP_KERNEL);
297 if (!crsbuf.pointer) {
298 err ("acpi_pciehprm: alloc %ld bytes for %s _CRS fail\n", (ulong)crsbuf.length, path_name);
299 return AE_NO_MEMORY;
300 }
301
302 status = acpi_get_current_resources (handle, &crsbuf);
303 if (ACPI_FAILURE(status)) {
304 err("acpi_pciehprm: %s _CRS fail=0x%x.\n", path_name, status);
305 kfree(crsbuf.pointer);
306 return status;
307 }
308
309 *retbuf = crsbuf.pointer;
310
311 return status;
312}
313
314static void free_pci_resource ( struct pci_resource *aprh)
315{
316 struct pci_resource *res, *next;
317
318 for (res = aprh; res; res = next) {
319 next = res->next;
320 kfree(res);
321 }
322}
323
324static void print_pci_resource ( struct pci_resource *aprh)
325{
326 struct pci_resource *res;
327
328 for (res = aprh; res; res = res->next)
329 dbg(" base= 0x%x length= 0x%x\n", res->base, res->length);
330}
331
332static void print_slot_resources( struct acpi_php_slot *aps)
333{
334 if (aps->bus_head) {
335 dbg(" BUS Resources:\n");
336 print_pci_resource (aps->bus_head);
337 }
338
339 if (aps->io_head) {
340 dbg(" IO Resources:\n");
341 print_pci_resource (aps->io_head);
342 }
343
344 if (aps->mem_head) {
345 dbg(" MEM Resources:\n");
346 print_pci_resource (aps->mem_head);
347 }
348
349 if (aps->p_mem_head) {
350 dbg(" PMEM Resources:\n");
351 print_pci_resource (aps->p_mem_head);
352 }
353}
354
355static void print_pci_resources( struct acpi_bridge *ab)
356{
357 if (ab->tbus_head) {
358 dbg(" Total BUS Resources:\n");
359 print_pci_resource (ab->tbus_head);
360 }
361 if (ab->bus_head) {
362 dbg(" BUS Resources:\n");
363 print_pci_resource (ab->bus_head);
364 }
365
366 if (ab->tio_head) {
367 dbg(" Total IO Resources:\n");
368 print_pci_resource (ab->tio_head);
369 }
370 if (ab->io_head) {
371 dbg(" IO Resources:\n");
372 print_pci_resource (ab->io_head);
373 }
374
375 if (ab->tmem_head) {
376 dbg(" Total MEM Resources:\n");
377 print_pci_resource (ab->tmem_head);
378 }
379 if (ab->mem_head) {
380 dbg(" MEM Resources:\n");
381 print_pci_resource (ab->mem_head);
382 }
383
384 if (ab->tp_mem_head) {
385 dbg(" Total PMEM Resources:\n");
386 print_pci_resource (ab->tp_mem_head);
387 }
388 if (ab->p_mem_head) {
389 dbg(" PMEM Resources:\n");
390 print_pci_resource (ab->p_mem_head);
391 }
392 if (ab->_hpp) {
393 dbg(" _HPP: cache_line_size=0x%x\n", ab->_hpp->cache_line_size);
394 dbg(" _HPP: latency timer =0x%x\n", ab->_hpp->latency_timer);
395 dbg(" _HPP: enable SERR =0x%x\n", ab->_hpp->enable_serr);
396 dbg(" _HPP: enable PERR =0x%x\n", ab->_hpp->enable_perr);
397 }
398}
399
400static int pciehprm_delete_resource(
401 struct pci_resource **aprh,
402 ulong base,
403 ulong size)
404{
405 struct pci_resource *res;
406 struct pci_resource *prevnode;
407 struct pci_resource *split_node;
408 ulong tbase;
409
410 pciehp_resource_sort_and_combine(aprh);
411
412 for (res = *aprh; res; res = res->next) {
413 if (res->base > base)
414 continue;
415
416 if ((res->base + res->length) < (base + size))
417 continue;
418
419 if (res->base < base) {
420 tbase = base;
421
422 if ((res->length - (tbase - res->base)) < size)
423 continue;
424
425 split_node = (struct pci_resource *) kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
426 if (!split_node)
427 return -ENOMEM;
428
429 split_node->base = res->base;
430 split_node->length = tbase - res->base;
431 res->base = tbase;
432 res->length -= split_node->length;
433
434 split_node->next = res->next;
435 res->next = split_node;
436 }
437
438 if (res->length >= size) {
439 split_node = (struct pci_resource*) kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
440 if (!split_node)
441 return -ENOMEM;
442
443 split_node->base = res->base + size;
444 split_node->length = res->length - size;
445 res->length = size;
446
447 split_node->next = res->next;
448 res->next = split_node;
449 }
450
451 if (*aprh == res) {
452 *aprh = res->next;
453 } else {
454 prevnode = *aprh;
455 while (prevnode->next != res)
456 prevnode = prevnode->next;
457
458 prevnode->next = res->next;
459 }
460 res->next = NULL;
461 kfree(res);
462 break;
463 }
464
465 return 0;
466}
467
468static int pciehprm_delete_resources(
469 struct pci_resource **aprh,
470 struct pci_resource *this
471 )
472{
473 struct pci_resource *res;
474
475 for (res = this; res; res = res->next)
476 pciehprm_delete_resource(aprh, res->base, res->length);
477
478 return 0;
479}
480
481static int pciehprm_add_resource(
482 struct pci_resource **aprh,
483 ulong base,
484 ulong size)
485{
486 struct pci_resource *res;
487
488 for (res = *aprh; res; res = res->next) {
489 if ((res->base + res->length) == base) {
490 res->length += size;
491 size = 0L;
492 break;
493 }
494 if (res->next == *aprh)
495 break;
496 }
497
498 if (size) {
499 res = kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
500 if (!res) {
501 err ("acpi_pciehprm: alloc for res fail\n");
502 return -ENOMEM;
503 }
504 memset(res, 0, sizeof (struct pci_resource));
505
506 res->base = base;
507 res->length = size;
508 res->next = *aprh;
509 *aprh = res;
510 }
511
512 return 0;
513}
514
515static int pciehprm_add_resources(
516 struct pci_resource **aprh,
517 struct pci_resource *this
518 )
519{
520 struct pci_resource *res;
521 int rc = 0;
522
523 for (res = this; res && !rc; res = res->next)
524 rc = pciehprm_add_resource(aprh, res->base, res->length);
525
526 return rc;
527}
528
529static void acpi_parse_io (
530 struct acpi_bridge *ab,
531 union acpi_resource_data *data
532 )
533{
534 struct acpi_resource_io *dataio;
535 dataio = (struct acpi_resource_io *) data;
536
537 dbg("Io Resource\n");
538 dbg(" %d bit decode\n", ACPI_DECODE_16 == dataio->io_decode ? 16:10);
539 dbg(" Range minimum base: %08X\n", dataio->min_base_address);
540 dbg(" Range maximum base: %08X\n", dataio->max_base_address);
541 dbg(" Alignment: %08X\n", dataio->alignment);
542 dbg(" Range Length: %08X\n", dataio->range_length);
543}
544
545static void acpi_parse_fixed_io (
546 struct acpi_bridge *ab,
547 union acpi_resource_data *data
548 )
549{
550 struct acpi_resource_fixed_io *datafio;
551 datafio = (struct acpi_resource_fixed_io *) data;
552
553 dbg("Fixed Io Resource\n");
554 dbg(" Range base address: %08X", datafio->base_address);
555 dbg(" Range length: %08X", datafio->range_length);
556}
557
558static void acpi_parse_address16_32 (
559 struct acpi_bridge *ab,
560 union acpi_resource_data *data,
561 acpi_resource_type id
562 )
563{
564 /*
565 * acpi_resource_address16 == acpi_resource_address32
566 * acpi_resource_address16 *data16 = (acpi_resource_address16 *) data;
567 */
568 struct acpi_resource_address32 *data32 = (struct acpi_resource_address32 *) data;
569 struct pci_resource **aprh, **tprh;
570
571 if (id == ACPI_RSTYPE_ADDRESS16)
572 dbg("acpi_pciehprm:16-Bit Address Space Resource\n");
573 else
574 dbg("acpi_pciehprm:32-Bit Address Space Resource\n");
575
576 switch (data32->resource_type) {
577 case ACPI_MEMORY_RANGE:
578 dbg(" Resource Type: Memory Range\n");
579 aprh = &ab->mem_head;
580 tprh = &ab->tmem_head;
581
582 switch (data32->attribute.memory.cache_attribute) {
583 case ACPI_NON_CACHEABLE_MEMORY:
584 dbg(" Type Specific: Noncacheable memory\n");
585 break;
586 case ACPI_CACHABLE_MEMORY:
587 dbg(" Type Specific: Cacheable memory\n");
588 break;
589 case ACPI_WRITE_COMBINING_MEMORY:
590 dbg(" Type Specific: Write-combining memory\n");
591 break;
592 case ACPI_PREFETCHABLE_MEMORY:
593 aprh = &ab->p_mem_head;
594 dbg(" Type Specific: Prefetchable memory\n");
595 break;
596 default:
597 dbg(" Type Specific: Invalid cache attribute\n");
598 break;
599 }
600
601 dbg(" Type Specific: Read%s\n", ACPI_READ_WRITE_MEMORY == data32->attribute.memory.read_write_attribute ? "/Write":" Only");
602 break;
603
604 case ACPI_IO_RANGE:
605 dbg(" Resource Type: I/O Range\n");
606 aprh = &ab->io_head;
607 tprh = &ab->tio_head;
608
609 switch (data32->attribute.io.range_attribute) {
610 case ACPI_NON_ISA_ONLY_RANGES:
611 dbg(" Type Specific: Non-ISA Io Addresses\n");
612 break;
613 case ACPI_ISA_ONLY_RANGES:
614 dbg(" Type Specific: ISA Io Addresses\n");
615 break;
616 case ACPI_ENTIRE_RANGE:
617 dbg(" Type Specific: ISA and non-ISA Io Addresses\n");
618 break;
619 default:
620 dbg(" Type Specific: Invalid range attribute\n");
621 break;
622 }
623 break;
624
625 case ACPI_BUS_NUMBER_RANGE:
626 dbg(" Resource Type: Bus Number Range(fixed)\n");
627 /* fixup to be compatible with the rest of php driver */
628 data32->min_address_range++;
629 data32->address_length--;
630 aprh = &ab->bus_head;
631 tprh = &ab->tbus_head;
632 break;
633 default:
634 dbg(" Resource Type: Invalid resource type. Exiting.\n");
635 return;
636 }
637
638 dbg(" Resource %s\n", ACPI_CONSUMER == data32->producer_consumer ? "Consumer":"Producer");
639 dbg(" %s decode\n", ACPI_SUB_DECODE == data32->decode ? "Subtractive":"Positive");
640 dbg(" Min address is %s fixed\n", ACPI_ADDRESS_FIXED == data32->min_address_fixed ? "":"not");
641 dbg(" Max address is %s fixed\n", ACPI_ADDRESS_FIXED == data32->max_address_fixed ? "":"not");
642 dbg(" Granularity: %08X\n", data32->granularity);
643 dbg(" Address range min: %08X\n", data32->min_address_range);
644 dbg(" Address range max: %08X\n", data32->max_address_range);
645 dbg(" Address translation offset: %08X\n", data32->address_translation_offset);
646 dbg(" Address Length: %08X\n", data32->address_length);
647
648 if (0xFF != data32->resource_source.index) {
649 dbg(" Resource Source Index: %X\n", data32->resource_source.index);
650 /* dbg(" Resource Source: %s\n", data32->resource_source.string_ptr); */
651 }
652
653 pciehprm_add_resource(aprh, data32->min_address_range, data32->address_length);
654}
655
656static acpi_status acpi_parse_crs(
657 struct acpi_bridge *ab,
658 struct acpi_resource *crsbuf
659 )
660{
661 acpi_status status = AE_OK;
662 struct acpi_resource *resource = crsbuf;
663 u8 count = 0;
664 u8 done = 0;
665
666 while (!done) {
667 dbg("acpi_pciehprm: PCI bus 0x%x Resource structure %x.\n", ab->bus, count++);
668 switch (resource->id) {
669 case ACPI_RSTYPE_IRQ:
670 dbg("Irq -------- Resource\n");
671 break;
672 case ACPI_RSTYPE_DMA:
673 dbg("DMA -------- Resource\n");
674 break;
675 case ACPI_RSTYPE_START_DPF:
676 dbg("Start DPF -------- Resource\n");
677 break;
678 case ACPI_RSTYPE_END_DPF:
679 dbg("End DPF -------- Resource\n");
680 break;
681 case ACPI_RSTYPE_IO:
682 acpi_parse_io (ab, &resource->data);
683 break;
684 case ACPI_RSTYPE_FIXED_IO:
685 acpi_parse_fixed_io (ab, &resource->data);
686 break;
687 case ACPI_RSTYPE_VENDOR:
688 dbg("Vendor -------- Resource\n");
689 break;
690 case ACPI_RSTYPE_END_TAG:
691 dbg("End_tag -------- Resource\n");
692 done = 1;
693 break;
694 case ACPI_RSTYPE_MEM24:
695 dbg("Mem24 -------- Resource\n");
696 break;
697 case ACPI_RSTYPE_MEM32:
698 dbg("Mem32 -------- Resource\n");
699 break;
700 case ACPI_RSTYPE_FIXED_MEM32:
701 dbg("Fixed Mem32 -------- Resource\n");
702 break;
703 case ACPI_RSTYPE_ADDRESS16:
704 acpi_parse_address16_32(ab, &resource->data, ACPI_RSTYPE_ADDRESS16);
705 break;
706 case ACPI_RSTYPE_ADDRESS32:
707 acpi_parse_address16_32(ab, &resource->data, ACPI_RSTYPE_ADDRESS32);
708 break;
709 case ACPI_RSTYPE_ADDRESS64:
710 info("Address64 -------- Resource unparsed\n");
711 break;
712 case ACPI_RSTYPE_EXT_IRQ:
713 dbg("Ext Irq -------- Resource\n");
714 break;
715 default:
716 dbg("Invalid -------- resource type 0x%x\n", resource->id);
717 break;
718 }
719
720 resource = (struct acpi_resource *) ((char *)resource + resource->length);
721 }
722
723 return status;
724}
725
726static acpi_status acpi_get_crs( struct acpi_bridge *ab)
727{
728 acpi_status status;
729 struct acpi_resource *crsbuf;
730
731 status = acpi_evaluate_crs(ab->handle, &crsbuf);
732 if (ACPI_SUCCESS(status)) {
733 status = acpi_parse_crs(ab, crsbuf);
734 kfree(crsbuf);
735
736 pciehp_resource_sort_and_combine(&ab->bus_head);
737 pciehp_resource_sort_and_combine(&ab->io_head);
738 pciehp_resource_sort_and_combine(&ab->mem_head);
739 pciehp_resource_sort_and_combine(&ab->p_mem_head);
740
741 pciehprm_add_resources (&ab->tbus_head, ab->bus_head);
742 pciehprm_add_resources (&ab->tio_head, ab->io_head);
743 pciehprm_add_resources (&ab->tmem_head, ab->mem_head);
744 pciehprm_add_resources (&ab->tp_mem_head, ab->p_mem_head);
745 }
746
747 return status;
748}
749
750/* find acpi_bridge downword from ab. */ 256/* find acpi_bridge downword from ab. */
751static struct acpi_bridge * 257static struct acpi_bridge *
752find_acpi_bridge_by_bus( 258find_acpi_bridge_by_bus(
@@ -1064,14 +570,6 @@ static struct acpi_bridge * add_host_bridge(
1064 ab->scanned = 0; 570 ab->scanned = 0;
1065 ab->type = BRIDGE_TYPE_HOST; 571 ab->type = BRIDGE_TYPE_HOST;
1066 572
1067 /* get root pci bridge's current resources */
1068 status = acpi_get_crs(ab);
1069 if (ACPI_FAILURE(status)) {
1070 err("acpi_pciehprm:%s evaluate _CRS fail=0x%x\n", path_name, status);
1071 kfree(ab);
1072 return NULL;
1073 }
1074
1075 status = pci_osc_control_set (OSC_PCI_EXPRESS_NATIVE_HP_CONTROL); 573 status = pci_osc_control_set (OSC_PCI_EXPRESS_NATIVE_HP_CONTROL);
1076 if (ACPI_FAILURE(status)) { 574 if (ACPI_FAILURE(status)) {
1077 err("%s: status %x\n", __FUNCTION__, status); 575 err("%s: status %x\n", __FUNCTION__, status);
@@ -1179,11 +677,6 @@ static void free_a_slot(struct acpi_php_slot *aps)
1179{ 677{
1180 dbg(" free a php func of slot(0x%02x) on PCI b:d:f=0x%02x:%02x:%02x\n", aps->sun, aps->bus, aps->dev, aps->fun); 678 dbg(" free a php func of slot(0x%02x) on PCI b:d:f=0x%02x:%02x:%02x\n", aps->sun, aps->bus, aps->dev, aps->fun);
1181 679
1182 free_pci_resource (aps->io_head);
1183 free_pci_resource (aps->bus_head);
1184 free_pci_resource (aps->mem_head);
1185 free_pci_resource (aps->p_mem_head);
1186
1187 kfree(aps); 680 kfree(aps);
1188} 681}
1189 682
@@ -1208,15 +701,6 @@ static void free_a_bridge( struct acpi_bridge *ab)
1208 free_a_slot(aps); 701 free_a_slot(aps);
1209 } 702 }
1210 703
1211 free_pci_resource (ab->io_head);
1212 free_pci_resource (ab->tio_head);
1213 free_pci_resource (ab->bus_head);
1214 free_pci_resource (ab->tbus_head);
1215 free_pci_resource (ab->mem_head);
1216 free_pci_resource (ab->tmem_head);
1217 free_pci_resource (ab->p_mem_head);
1218 free_pci_resource (ab->tp_mem_head);
1219
1220 kfree(ab); 704 kfree(ab);
1221} 705}
1222 706
@@ -1266,48 +750,6 @@ static int get_number_of_slots (
1266 return slot_num; 750 return slot_num;
1267} 751}
1268 752
1269static int print_acpi_resources (struct acpi_bridge *ab)
1270{
1271 struct acpi_php_slot *aps;
1272 int i;
1273
1274 switch (ab->type) {
1275 case BRIDGE_TYPE_HOST:
1276 dbg("PCI HOST Bridge (%x) [%s]\n", ab->bus, acpi_path_name(ab->handle));
1277 break;
1278 case BRIDGE_TYPE_P2P:
1279 dbg("PCI P2P Bridge (%x-%x) [%s]\n", ab->pbus, ab->bus, acpi_path_name(ab->handle));
1280 break;
1281 };
1282
1283 print_pci_resources (ab);
1284
1285 for ( i = -1, aps = ab->slots; aps; aps = aps->next) {
1286 if (aps->dev == i)
1287 continue;
1288 dbg(" Slot sun(%x) s:b:d:f(%02x:%02x:%02x:%02x)\n", aps->sun, aps->seg, aps->bus, aps->dev, aps->fun);
1289 print_slot_resources(aps);
1290 i = aps->dev;
1291 }
1292
1293 if (ab->child)
1294 print_acpi_resources (ab->child);
1295
1296 if (ab->next)
1297 print_acpi_resources (ab->next);
1298
1299 return 0;
1300}
1301
1302int pciehprm_print_pirt(void)
1303{
1304 dbg("PCIEHPRM ACPI Slots\n");
1305 if (acpi_bridges_head)
1306 print_acpi_resources (acpi_bridges_head);
1307
1308 return 0;
1309}
1310
1311static struct acpi_php_slot * get_acpi_slot ( 753static struct acpi_php_slot * get_acpi_slot (
1312 struct acpi_bridge *ab, 754 struct acpi_bridge *ab,
1313 u32 sun 755 u32 sun
@@ -1349,288 +791,6 @@ void * pciehprm_get_slot(struct slot *slot)
1349} 791}
1350#endif 792#endif
1351 793
1352static void pciehprm_dump_func_res( struct pci_func *fun)
1353{
1354 struct pci_func *func = fun;
1355
1356 if (func->bus_head) {
1357 dbg(": BUS Resources:\n");
1358 print_pci_resource (func->bus_head);
1359 }
1360 if (func->io_head) {
1361 dbg(": IO Resources:\n");
1362 print_pci_resource (func->io_head);
1363 }
1364 if (func->mem_head) {
1365 dbg(": MEM Resources:\n");
1366 print_pci_resource (func->mem_head);
1367 }
1368 if (func->p_mem_head) {
1369 dbg(": PMEM Resources:\n");
1370 print_pci_resource (func->p_mem_head);
1371 }
1372}
1373
1374static void pciehprm_dump_ctrl_res( struct controller *ctlr)
1375{
1376 struct controller *ctrl = ctlr;
1377
1378 if (ctrl->bus_head) {
1379 dbg(": BUS Resources:\n");
1380 print_pci_resource (ctrl->bus_head);
1381 }
1382 if (ctrl->io_head) {
1383 dbg(": IO Resources:\n");
1384 print_pci_resource (ctrl->io_head);
1385 }
1386 if (ctrl->mem_head) {
1387 dbg(": MEM Resources:\n");
1388 print_pci_resource (ctrl->mem_head);
1389 }
1390 if (ctrl->p_mem_head) {
1391 dbg(": PMEM Resources:\n");
1392 print_pci_resource (ctrl->p_mem_head);
1393 }
1394}
1395
1396static int pciehprm_get_used_resources (
1397 struct controller *ctrl,
1398 struct pci_func *func
1399 )
1400{
1401 return pciehp_save_used_resources (ctrl, func, !DISABLE_CARD);
1402}
1403
1404static int configure_existing_function(
1405 struct controller *ctrl,
1406 struct pci_func *func
1407 )
1408{
1409 int rc;
1410
1411 /* see how much resources the func has used. */
1412 rc = pciehprm_get_used_resources (ctrl, func);
1413
1414 if (!rc) {
1415 /* subtract the resources used by the func from ctrl resources */
1416 rc = pciehprm_delete_resources (&ctrl->bus_head, func->bus_head);
1417 rc |= pciehprm_delete_resources (&ctrl->io_head, func->io_head);
1418 rc |= pciehprm_delete_resources (&ctrl->mem_head, func->mem_head);
1419 rc |= pciehprm_delete_resources (&ctrl->p_mem_head, func->p_mem_head);
1420 if (rc)
1421 warn("aCEF: cannot del used resources\n");
1422 } else
1423 err("aCEF: cannot get used resources\n");
1424
1425 return rc;
1426}
1427
1428static int bind_pci_resources_to_slots ( struct controller *ctrl)
1429{
1430 struct pci_func *func, new_func;
1431 int busn = ctrl->slot_bus;
1432 int devn, funn;
1433 u32 vid;
1434
1435 for (devn = 0; devn < 32; devn++) {
1436 for (funn = 0; funn < 8; funn++) {
1437 /*
1438 if (devn == ctrl->device && funn == ctrl->function)
1439 continue;
1440 */
1441 /* find out if this entry is for an occupied slot */
1442 vid = 0xFFFFFFFF;
1443 pci_bus_read_config_dword(ctrl->pci_dev->subordinate, PCI_DEVFN(devn, funn), PCI_VENDOR_ID, &vid);
1444
1445 if (vid != 0xFFFFFFFF) {
1446 dbg("%s: vid = %x\n", __FUNCTION__, vid);
1447 func = pciehp_slot_find(busn, devn, funn);
1448 if (!func) {
1449 memset(&new_func, 0, sizeof(struct pci_func));
1450 new_func.bus = busn;
1451 new_func.device = devn;
1452 new_func.function = funn;
1453 new_func.is_a_board = 1;
1454 configure_existing_function(ctrl, &new_func);
1455 pciehprm_dump_func_res(&new_func);
1456 } else {
1457 configure_existing_function(ctrl, func);
1458 pciehprm_dump_func_res(func);
1459 }
1460 dbg("aCCF:existing PCI 0x%x Func ResourceDump\n", ctrl->bus);
1461 }
1462 }
1463 }
1464
1465 return 0;
1466}
1467
1468static int bind_pci_resources(
1469 struct controller *ctrl,
1470 struct acpi_bridge *ab
1471 )
1472{
1473 int status = 0;
1474
1475 if (ab->bus_head) {
1476 dbg("bapr: BUS Resources add on PCI 0x%x\n", ab->bus);
1477 status = pciehprm_add_resources (&ctrl->bus_head, ab->bus_head);
1478 if (pciehprm_delete_resources (&ab->bus_head, ctrl->bus_head))
1479 warn("bapr: cannot sub BUS Resource on PCI 0x%x\n", ab->bus);
1480 if (status) {
1481 err("bapr: BUS Resource add on PCI 0x%x: fail=0x%x\n", ab->bus, status);
1482 return status;
1483 }
1484 } else
1485 info("bapr: No BUS Resource on PCI 0x%x.\n", ab->bus);
1486
1487 if (ab->io_head) {
1488 dbg("bapr: IO Resources add on PCI 0x%x\n", ab->bus);
1489 status = pciehprm_add_resources (&ctrl->io_head, ab->io_head);
1490 if (pciehprm_delete_resources (&ab->io_head, ctrl->io_head))
1491 warn("bapr: cannot sub IO Resource on PCI 0x%x\n", ab->bus);
1492 if (status) {
1493 err("bapr: IO Resource add on PCI 0x%x: fail=0x%x\n", ab->bus, status);
1494 return status;
1495 }
1496 } else
1497 info("bapr: No IO Resource on PCI 0x%x.\n", ab->bus);
1498
1499 if (ab->mem_head) {
1500 dbg("bapr: MEM Resources add on PCI 0x%x\n", ab->bus);
1501 status = pciehprm_add_resources (&ctrl->mem_head, ab->mem_head);
1502 if (pciehprm_delete_resources (&ab->mem_head, ctrl->mem_head))
1503 warn("bapr: cannot sub MEM Resource on PCI 0x%x\n", ab->bus);
1504 if (status) {
1505 err("bapr: MEM Resource add on PCI 0x%x: fail=0x%x\n", ab->bus, status);
1506 return status;
1507 }
1508 } else
1509 info("bapr: No MEM Resource on PCI 0x%x.\n", ab->bus);
1510
1511 if (ab->p_mem_head) {
1512 dbg("bapr: PMEM Resources add on PCI 0x%x\n", ab->bus);
1513 status = pciehprm_add_resources (&ctrl->p_mem_head, ab->p_mem_head);
1514 if (pciehprm_delete_resources (&ab->p_mem_head, ctrl->p_mem_head))
1515 warn("bapr: cannot sub PMEM Resource on PCI 0x%x\n", ab->bus);
1516 if (status) {
1517 err("bapr: PMEM Resource add on PCI 0x%x: fail=0x%x\n", ab->bus, status);
1518 return status;
1519 }
1520 } else
1521 info("bapr: No PMEM Resource on PCI 0x%x.\n", ab->bus);
1522
1523 return status;
1524}
1525
1526static int no_pci_resources( struct acpi_bridge *ab)
1527{
1528 return !(ab->p_mem_head || ab->mem_head || ab->io_head || ab->bus_head);
1529}
1530
1531static int find_pci_bridge_resources (
1532 struct controller *ctrl,
1533 struct acpi_bridge *ab
1534 )
1535{
1536 int rc = 0;
1537 struct pci_func func;
1538
1539 memset(&func, 0, sizeof(struct pci_func));
1540
1541 func.bus = ab->pbus;
1542 func.device = ab->pdevice;
1543 func.function = ab->pfunction;
1544 func.is_a_board = 1;
1545
1546 /* Get used resources for this PCI bridge */
1547 rc = pciehp_save_used_resources (ctrl, &func, !DISABLE_CARD);
1548
1549 ab->io_head = func.io_head;
1550 ab->mem_head = func.mem_head;
1551 ab->p_mem_head = func.p_mem_head;
1552 ab->bus_head = func.bus_head;
1553 if (ab->bus_head)
1554 pciehprm_delete_resource(&ab->bus_head, ctrl->pci_dev->subordinate->number, 1);
1555
1556 return rc;
1557}
1558
1559static int get_pci_resources_from_bridge(
1560 struct controller *ctrl,
1561 struct acpi_bridge *ab
1562 )
1563{
1564 int rc = 0;
1565
1566 dbg("grfb: Get Resources for PCI 0x%x from actual PCI bridge 0x%x.\n", ctrl->bus, ab->bus);
1567
1568 rc = find_pci_bridge_resources (ctrl, ab);
1569
1570 pciehp_resource_sort_and_combine(&ab->bus_head);
1571 pciehp_resource_sort_and_combine(&ab->io_head);
1572 pciehp_resource_sort_and_combine(&ab->mem_head);
1573 pciehp_resource_sort_and_combine(&ab->p_mem_head);
1574
1575 pciehprm_add_resources (&ab->tbus_head, ab->bus_head);
1576 pciehprm_add_resources (&ab->tio_head, ab->io_head);
1577 pciehprm_add_resources (&ab->tmem_head, ab->mem_head);
1578 pciehprm_add_resources (&ab->tp_mem_head, ab->p_mem_head);
1579
1580 return rc;
1581}
1582
1583static int get_pci_resources(
1584 struct controller *ctrl,
1585 struct acpi_bridge *ab
1586 )
1587{
1588 int rc = 0;
1589
1590 if (no_pci_resources(ab)) {
1591 dbg("spbr:PCI 0x%x has no resources. Get parent resources.\n", ab->bus);
1592 rc = get_pci_resources_from_bridge(ctrl, ab);
1593 }
1594
1595 return rc;
1596}
1597
1598/*
1599 * Get resources for this ctrl.
1600 * 1. get total resources from ACPI _CRS or bridge (this ctrl)
1601 * 2. find used resources of existing adapters
1602 * 3. subtract used resources from total resources
1603 */
1604int pciehprm_find_available_resources( struct controller *ctrl)
1605{
1606 int rc = 0;
1607 struct acpi_bridge *ab;
1608
1609 ab = find_acpi_bridge_by_bus(acpi_bridges_head, ctrl->seg, ctrl->pci_dev->subordinate->number);
1610 if (!ab) {
1611 err("pfar:cannot locate acpi bridge of PCI 0x%x.\n", ctrl->pci_dev->subordinate->number);
1612 return -1;
1613 }
1614 if (no_pci_resources(ab)) {
1615 rc = get_pci_resources(ctrl, ab);
1616 if (rc) {
1617 err("pfar:cannot get pci resources of PCI 0x%x.\n", ctrl->pci_dev->subordinate->number);
1618 return -1;
1619 }
1620 }
1621
1622 rc = bind_pci_resources(ctrl, ab);
1623 dbg("pfar:pre-Bind PCI 0x%x Ctrl Resource Dump\n", ctrl->pci_dev->subordinate->number);
1624 pciehprm_dump_ctrl_res(ctrl);
1625
1626 bind_pci_resources_to_slots (ctrl);
1627
1628 dbg("pfar:post-Bind PCI 0x%x Ctrl Resource Dump\n", ctrl->pci_dev->subordinate->number);
1629 pciehprm_dump_ctrl_res(ctrl);
1630
1631 return rc;
1632}
1633
1634int pciehprm_set_hpp( 794int pciehprm_set_hpp(
1635 struct controller *ctrl, 795 struct controller *ctrl,
1636 struct pci_func *func, 796 struct pci_func *func,
diff --git a/drivers/pci/hotplug/pciehprm_nonacpi.c b/drivers/pci/hotplug/pciehprm_nonacpi.c
index 76c727c74cc0..ed68c3dd0f08 100644
--- a/drivers/pci/hotplug/pciehprm_nonacpi.c
+++ b/drivers/pci/hotplug/pciehprm_nonacpi.c
@@ -35,12 +35,7 @@
35#include <linux/pci.h> 35#include <linux/pci.h>
36#include <linux/init.h> 36#include <linux/init.h>
37#include <linux/slab.h> 37#include <linux/slab.h>
38
39#include <asm/uaccess.h> 38#include <asm/uaccess.h>
40#ifdef CONFIG_IA64
41#include <asm/iosapic.h>
42#endif
43
44#include "pciehp.h" 39#include "pciehp.h"
45#include "pciehprm.h" 40#include "pciehprm.h"
46#include "pciehprm_nonacpi.h" 41#include "pciehprm_nonacpi.h"
@@ -51,11 +46,6 @@ void pciehprm_cleanup(void)
51 return; 46 return;
52} 47}
53 48
54int pciehprm_print_pirt(void)
55{
56 return 0;
57}
58
59int pciehprm_get_physical_slot_number(struct controller *ctrl, u32 *sun, u8 busnum, u8 devnum) 49int pciehprm_get_physical_slot_number(struct controller *ctrl, u32 *sun, u8 busnum, u8 devnum)
60{ 50{
61 51
@@ -63,343 +53,6 @@ int pciehprm_get_physical_slot_number(struct controller *ctrl, u32 *sun, u8 busn
63 return 0; 53 return 0;
64} 54}
65 55
66
67static void print_pci_resource ( struct pci_resource *aprh)
68{
69 struct pci_resource *res;
70
71 for (res = aprh; res; res = res->next)
72 dbg(" base= 0x%x length= 0x%x\n", res->base, res->length);
73}
74
75
76static void phprm_dump_func_res( struct pci_func *fun)
77{
78 struct pci_func *func = fun;
79
80 if (func->bus_head) {
81 dbg(": BUS Resources:\n");
82 print_pci_resource (func->bus_head);
83 }
84 if (func->io_head) {
85 dbg(": IO Resources:\n");
86 print_pci_resource (func->io_head);
87 }
88 if (func->mem_head) {
89 dbg(": MEM Resources:\n");
90 print_pci_resource (func->mem_head);
91 }
92 if (func->p_mem_head) {
93 dbg(": PMEM Resources:\n");
94 print_pci_resource (func->p_mem_head);
95 }
96}
97
98static int phprm_get_used_resources (
99 struct controller *ctrl,
100 struct pci_func *func
101 )
102{
103 return pciehp_save_used_resources (ctrl, func, !DISABLE_CARD);
104}
105
106static int phprm_delete_resource(
107 struct pci_resource **aprh,
108 ulong base,
109 ulong size)
110{
111 struct pci_resource *res;
112 struct pci_resource *prevnode;
113 struct pci_resource *split_node;
114 ulong tbase;
115
116 pciehp_resource_sort_and_combine(aprh);
117
118 for (res = *aprh; res; res = res->next) {
119 if (res->base > base)
120 continue;
121
122 if ((res->base + res->length) < (base + size))
123 continue;
124
125 if (res->base < base) {
126 tbase = base;
127
128 if ((res->length - (tbase - res->base)) < size)
129 continue;
130
131 split_node = (struct pci_resource *) kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
132 if (!split_node)
133 return -ENOMEM;
134
135 split_node->base = res->base;
136 split_node->length = tbase - res->base;
137 res->base = tbase;
138 res->length -= split_node->length;
139
140 split_node->next = res->next;
141 res->next = split_node;
142 }
143
144 if (res->length >= size) {
145 split_node = (struct pci_resource*) kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
146 if (!split_node)
147 return -ENOMEM;
148
149 split_node->base = res->base + size;
150 split_node->length = res->length - size;
151 res->length = size;
152
153 split_node->next = res->next;
154 res->next = split_node;
155 }
156
157 if (*aprh == res) {
158 *aprh = res->next;
159 } else {
160 prevnode = *aprh;
161 while (prevnode->next != res)
162 prevnode = prevnode->next;
163
164 prevnode->next = res->next;
165 }
166 res->next = NULL;
167 kfree(res);
168 break;
169 }
170
171 return 0;
172}
173
174
175static int phprm_delete_resources(
176 struct pci_resource **aprh,
177 struct pci_resource *this
178 )
179{
180 struct pci_resource *res;
181
182 for (res = this; res; res = res->next)
183 phprm_delete_resource(aprh, res->base, res->length);
184
185 return 0;
186}
187
188
189static int configure_existing_function(
190 struct controller *ctrl,
191 struct pci_func *func
192 )
193{
194 int rc;
195
196 /* see how much resources the func has used. */
197 rc = phprm_get_used_resources (ctrl, func);
198
199 if (!rc) {
200 /* subtract the resources used by the func from ctrl resources */
201 rc = phprm_delete_resources (&ctrl->bus_head, func->bus_head);
202 rc |= phprm_delete_resources (&ctrl->io_head, func->io_head);
203 rc |= phprm_delete_resources (&ctrl->mem_head, func->mem_head);
204 rc |= phprm_delete_resources (&ctrl->p_mem_head, func->p_mem_head);
205 if (rc)
206 warn("aCEF: cannot del used resources\n");
207 } else
208 err("aCEF: cannot get used resources\n");
209
210 return rc;
211}
212
213static int pciehprm_delete_resource(
214 struct pci_resource **aprh,
215 ulong base,
216 ulong size)
217{
218 struct pci_resource *res;
219 struct pci_resource *prevnode;
220 struct pci_resource *split_node;
221 ulong tbase;
222
223 pciehp_resource_sort_and_combine(aprh);
224
225 for (res = *aprh; res; res = res->next) {
226 if (res->base > base)
227 continue;
228
229 if ((res->base + res->length) < (base + size))
230 continue;
231
232 if (res->base < base) {
233 tbase = base;
234
235 if ((res->length - (tbase - res->base)) < size)
236 continue;
237
238 split_node = (struct pci_resource *) kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
239 if (!split_node)
240 return -ENOMEM;
241
242 split_node->base = res->base;
243 split_node->length = tbase - res->base;
244 res->base = tbase;
245 res->length -= split_node->length;
246
247 split_node->next = res->next;
248 res->next = split_node;
249 }
250
251 if (res->length >= size) {
252 split_node = (struct pci_resource*) kmalloc(sizeof(struct pci_resource), GFP_KERNEL);
253 if (!split_node)
254 return -ENOMEM;
255
256 split_node->base = res->base + size;
257 split_node->length = res->length - size;
258 res->length = size;
259
260 split_node->next = res->next;
261 res->next = split_node;
262 }
263
264 if (*aprh == res) {
265 *aprh = res->next;
266 } else {
267 prevnode = *aprh;
268 while (prevnode->next != res)
269 prevnode = prevnode->next;
270
271 prevnode->next = res->next;
272 }
273 res->next = NULL;
274 kfree(res);
275 break;
276 }
277
278 return 0;
279}
280
281static int bind_pci_resources_to_slots ( struct controller *ctrl)
282{
283 struct pci_func *func, new_func;
284 int busn = ctrl->slot_bus;
285 int devn, funn;
286 u32 vid;
287
288 for (devn = 0; devn < 32; devn++) {
289 for (funn = 0; funn < 8; funn++) {
290 /*
291 if (devn == ctrl->device && funn == ctrl->function)
292 continue;
293 */
294 /* find out if this entry is for an occupied slot */
295 vid = 0xFFFFFFFF;
296
297 pci_bus_read_config_dword(ctrl->pci_dev->subordinate, PCI_DEVFN(devn, funn), PCI_VENDOR_ID, &vid);
298
299 if (vid != 0xFFFFFFFF) {
300 dbg("%s: vid = %x bus %x dev %x fun %x\n", __FUNCTION__,
301 vid, busn, devn, funn);
302 func = pciehp_slot_find(busn, devn, funn);
303 dbg("%s: func = %p\n", __FUNCTION__,func);
304 if (!func) {
305 memset(&new_func, 0, sizeof(struct pci_func));
306 new_func.bus = busn;
307 new_func.device = devn;
308 new_func.function = funn;
309 new_func.is_a_board = 1;
310 configure_existing_function(ctrl, &new_func);
311 phprm_dump_func_res(&new_func);
312 } else {
313 configure_existing_function(ctrl, func);
314 phprm_dump_func_res(func);
315 }
316 dbg("aCCF:existing PCI 0x%x Func ResourceDump\n", ctrl->bus);
317 }
318 }
319 }
320
321 return 0;
322}
323
324static void phprm_dump_ctrl_res( struct controller *ctlr)
325{
326 struct controller *ctrl = ctlr;
327
328 if (ctrl->bus_head) {
329 dbg(": BUS Resources:\n");
330 print_pci_resource (ctrl->bus_head);
331 }
332 if (ctrl->io_head) {
333 dbg(": IO Resources:\n");
334 print_pci_resource (ctrl->io_head);
335 }
336 if (ctrl->mem_head) {
337 dbg(": MEM Resources:\n");
338 print_pci_resource (ctrl->mem_head);
339 }
340 if (ctrl->p_mem_head) {
341 dbg(": PMEM Resources:\n");
342 print_pci_resource (ctrl->p_mem_head);
343 }
344}
345
346/*
347 * phprm_find_available_resources
348 *
349 * Finds available memory, IO, and IRQ resources for programming
350 * devices which may be added to the system
351 * this function is for hot plug ADD!
352 *
353 * returns 0 if success
354 */
355int pciehprm_find_available_resources(struct controller *ctrl)
356{
357 struct pci_func func;
358 u32 rc;
359
360 memset(&func, 0, sizeof(struct pci_func));
361
362 func.bus = ctrl->bus;
363 func.device = ctrl->device;
364 func.function = ctrl->function;
365 func.is_a_board = 1;
366
367 /* Get resources for this PCI bridge */
368 rc = pciehp_save_used_resources (ctrl, &func, !DISABLE_CARD);
369 dbg("%s: pciehp_save_used_resources rc = %d\n", __FUNCTION__, rc);
370
371 if (func.mem_head)
372 func.mem_head->next = ctrl->mem_head;
373 ctrl->mem_head = func.mem_head;
374
375 if (func.p_mem_head)
376 func.p_mem_head->next = ctrl->p_mem_head;
377 ctrl->p_mem_head = func.p_mem_head;
378
379 if (func.io_head)
380 func.io_head->next = ctrl->io_head;
381 ctrl->io_head = func.io_head;
382
383 if(func.bus_head)
384 func.bus_head->next = ctrl->bus_head;
385 ctrl->bus_head = func.bus_head;
386
387 if (ctrl->bus_head)
388 pciehprm_delete_resource(&ctrl->bus_head, ctrl->pci_dev->subordinate->number, 1);
389
390 dbg("%s:pre-Bind PCI 0x%x Ctrl Resource Dump\n", __FUNCTION__, ctrl->bus);
391 phprm_dump_ctrl_res(ctrl);
392
393 dbg("%s: before bind_pci_resources_to slots\n", __FUNCTION__);
394
395 bind_pci_resources_to_slots (ctrl);
396
397 dbg("%s:post-Bind PCI 0x%x Ctrl Resource Dump\n", __FUNCTION__, ctrl->bus);
398 phprm_dump_ctrl_res(ctrl);
399
400 return (rc);
401}
402
403int pciehprm_set_hpp( 56int pciehprm_set_hpp(
404 struct controller *ctrl, 57 struct controller *ctrl,
405 struct pci_func *func, 58 struct pci_func *func,