aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@g5.osdl.org>2005-07-13 18:48:33 -0400
committerLinus Torvalds <torvalds@g5.osdl.org>2005-07-13 18:48:33 -0400
commit514fd7fd01d378a7b5584c657d9807fc28f22079 (patch)
treebda3910b7737a4fac464792657ffedcba185d799 /arch
parent1e279dd855d15b72364b4103f872d67d8592647e (diff)
parent99ad25a313bda566a346b46a6015afa65bc0a02b (diff)
Merge master.kernel.org:/pub/scm/linux/kernel/git/aegl/linux-2.6
Diffstat (limited to 'arch')
-rw-r--r--arch/ia64/Kconfig7
-rw-r--r--arch/ia64/configs/sn2_defconfig1
-rw-r--r--arch/ia64/kernel/setup.c37
-rw-r--r--arch/ia64/lib/flush.S46
-rw-r--r--arch/ia64/pci/pci.c12
-rw-r--r--arch/ia64/sn/kernel/io_init.c20
-rw-r--r--arch/ia64/sn/kernel/xpc_channel.c8
-rw-r--r--arch/ia64/sn/pci/pci_dma.c16
-rw-r--r--arch/ia64/sn/pci/pcibr/pcibr_provider.c10
-rw-r--r--arch/ia64/sn/pci/tioca_provider.c4
10 files changed, 126 insertions, 35 deletions
diff --git a/arch/ia64/Kconfig b/arch/ia64/Kconfig
index 2e08942339ad..cbb3e0cef93a 100644
--- a/arch/ia64/Kconfig
+++ b/arch/ia64/Kconfig
@@ -220,13 +220,6 @@ config IOSAPIC
220 depends on !IA64_HP_SIM 220 depends on !IA64_HP_SIM
221 default y 221 default y
222 222
223config IA64_SGI_SN_SIM
224 bool "SGI Medusa Simulator Support"
225 depends on IA64_SGI_SN2 || IA64_GENERIC
226 help
227 If you are compiling a kernel that will run under SGI's IA-64
228 simulator (Medusa) then say Y, otherwise say N.
229
230config IA64_SGI_SN_XP 223config IA64_SGI_SN_XP
231 tristate "Support communication between SGI SSIs" 224 tristate "Support communication between SGI SSIs"
232 select IA64_UNCACHED_ALLOCATOR 225 select IA64_UNCACHED_ALLOCATOR
diff --git a/arch/ia64/configs/sn2_defconfig b/arch/ia64/configs/sn2_defconfig
index c05613980300..04d0b00a2b8c 100644
--- a/arch/ia64/configs/sn2_defconfig
+++ b/arch/ia64/configs/sn2_defconfig
@@ -81,7 +81,6 @@ CONFIG_HOLES_IN_ZONE=y
81CONFIG_ARCH_DISCONTIGMEM_ENABLE=y 81CONFIG_ARCH_DISCONTIGMEM_ENABLE=y
82# CONFIG_IA64_CYCLONE is not set 82# CONFIG_IA64_CYCLONE is not set
83CONFIG_IOSAPIC=y 83CONFIG_IOSAPIC=y
84CONFIG_IA64_SGI_SN_SIM=y
85CONFIG_FORCE_MAX_ZONEORDER=18 84CONFIG_FORCE_MAX_ZONEORDER=18
86CONFIG_SMP=y 85CONFIG_SMP=y
87CONFIG_NR_CPUS=512 86CONFIG_NR_CPUS=512
diff --git a/arch/ia64/kernel/setup.c b/arch/ia64/kernel/setup.c
index 5c7c95737bbf..84f89da7c640 100644
--- a/arch/ia64/kernel/setup.c
+++ b/arch/ia64/kernel/setup.c
@@ -20,6 +20,7 @@
20 * 02/01/00 R.Seth fixed get_cpuinfo for SMP 20 * 02/01/00 R.Seth fixed get_cpuinfo for SMP
21 * 01/07/99 S.Eranian added the support for command line argument 21 * 01/07/99 S.Eranian added the support for command line argument
22 * 06/24/99 W.Drummond added boot_cpu_data. 22 * 06/24/99 W.Drummond added boot_cpu_data.
23 * 05/28/05 Z. Menyhart Dynamic stride size for "flush_icache_range()"
23 */ 24 */
24#include <linux/config.h> 25#include <linux/config.h>
25#include <linux/module.h> 26#include <linux/module.h>
@@ -85,6 +86,13 @@ EXPORT_SYMBOL(io_space);
85unsigned int num_io_spaces; 86unsigned int num_io_spaces;
86 87
87/* 88/*
89 * "flush_icache_range()" needs to know what processor dependent stride size to use
90 * when it makes i-cache(s) coherent with d-caches.
91 */
92#define I_CACHE_STRIDE_SHIFT 5 /* Safest way to go: 32 bytes by 32 bytes */
93unsigned long ia64_i_cache_stride_shift = ~0;
94
95/*
88 * The merge_mask variable needs to be set to (max(iommu_page_size(iommu)) - 1). This 96 * The merge_mask variable needs to be set to (max(iommu_page_size(iommu)) - 1). This
89 * mask specifies a mask of address bits that must be 0 in order for two buffers to be 97 * mask specifies a mask of address bits that must be 0 in order for two buffers to be
90 * mergeable by the I/O MMU (i.e., the end address of the first buffer and the start 98 * mergeable by the I/O MMU (i.e., the end address of the first buffer and the start
@@ -628,6 +636,12 @@ setup_per_cpu_areas (void)
628 /* start_kernel() requires this... */ 636 /* start_kernel() requires this... */
629} 637}
630 638
639/*
640 * Calculate the max. cache line size.
641 *
642 * In addition, the minimum of the i-cache stride sizes is calculated for
643 * "flush_icache_range()".
644 */
631static void 645static void
632get_max_cacheline_size (void) 646get_max_cacheline_size (void)
633{ 647{
@@ -641,6 +655,8 @@ get_max_cacheline_size (void)
641 printk(KERN_ERR "%s: ia64_pal_cache_summary() failed (status=%ld)\n", 655 printk(KERN_ERR "%s: ia64_pal_cache_summary() failed (status=%ld)\n",
642 __FUNCTION__, status); 656 __FUNCTION__, status);
643 max = SMP_CACHE_BYTES; 657 max = SMP_CACHE_BYTES;
658 /* Safest setup for "flush_icache_range()" */
659 ia64_i_cache_stride_shift = I_CACHE_STRIDE_SHIFT;
644 goto out; 660 goto out;
645 } 661 }
646 662
@@ -649,14 +665,31 @@ get_max_cacheline_size (void)
649 &cci); 665 &cci);
650 if (status != 0) { 666 if (status != 0) {
651 printk(KERN_ERR 667 printk(KERN_ERR
652 "%s: ia64_pal_cache_config_info(l=%lu) failed (status=%ld)\n", 668 "%s: ia64_pal_cache_config_info(l=%lu, 2) failed (status=%ld)\n",
653 __FUNCTION__, l, status); 669 __FUNCTION__, l, status);
654 max = SMP_CACHE_BYTES; 670 max = SMP_CACHE_BYTES;
671 /* The safest setup for "flush_icache_range()" */
672 cci.pcci_stride = I_CACHE_STRIDE_SHIFT;
673 cci.pcci_unified = 1;
655 } 674 }
656 line_size = 1 << cci.pcci_line_size; 675 line_size = 1 << cci.pcci_line_size;
657 if (line_size > max) 676 if (line_size > max)
658 max = line_size; 677 max = line_size;
659 } 678 if (!cci.pcci_unified) {
679 status = ia64_pal_cache_config_info(l,
680 /* cache_type (instruction)= */ 1,
681 &cci);
682 if (status != 0) {
683 printk(KERN_ERR
684 "%s: ia64_pal_cache_config_info(l=%lu, 1) failed (status=%ld)\n",
685 __FUNCTION__, l, status);
686 /* The safest setup for "flush_icache_range()" */
687 cci.pcci_stride = I_CACHE_STRIDE_SHIFT;
688 }
689 }
690 if (cci.pcci_stride < ia64_i_cache_stride_shift)
691 ia64_i_cache_stride_shift = cci.pcci_stride;
692 }
660 out: 693 out:
661 if (max > ia64_max_cacheline_size) 694 if (max > ia64_max_cacheline_size)
662 ia64_max_cacheline_size = max; 695 ia64_max_cacheline_size = max;
diff --git a/arch/ia64/lib/flush.S b/arch/ia64/lib/flush.S
index a1af9146cfdb..3e2cfa2c6d39 100644
--- a/arch/ia64/lib/flush.S
+++ b/arch/ia64/lib/flush.S
@@ -3,37 +3,59 @@
3 * 3 *
4 * Copyright (C) 1999-2001, 2005 Hewlett-Packard Co 4 * Copyright (C) 1999-2001, 2005 Hewlett-Packard Co
5 * David Mosberger-Tang <davidm@hpl.hp.com> 5 * David Mosberger-Tang <davidm@hpl.hp.com>
6 *
7 * 05/28/05 Zoltan Menyhart Dynamic stride size
6 */ 8 */
9
7#include <asm/asmmacro.h> 10#include <asm/asmmacro.h>
8#include <asm/page.h> 11
9 12
10 /* 13 /*
11 * flush_icache_range(start,end) 14 * flush_icache_range(start,end)
12 * Must flush range from start to end-1 but nothing else (need to 15 *
16 * Make i-cache(s) coherent with d-caches.
17 *
18 * Must deal with range from start to end-1 but nothing else (need to
13 * be careful not to touch addresses that may be unmapped). 19 * be careful not to touch addresses that may be unmapped).
20 *
21 * Note: "in0" and "in1" are preserved for debugging purposes.
14 */ 22 */
15GLOBAL_ENTRY(flush_icache_range) 23GLOBAL_ENTRY(flush_icache_range)
24
16 .prologue 25 .prologue
17 alloc r2=ar.pfs,2,0,0,0 26 alloc r2=ar.pfs,2,0,0,0
18 sub r8=in1,in0,1 27 movl r3=ia64_i_cache_stride_shift
28 mov r21=1
29 ;;
30 ld8 r20=[r3] // r20: stride shift
31 sub r22=in1,r0,1 // last byte address
19 ;; 32 ;;
20 shr.u r8=r8,5 // we flush 32 bytes per iteration 33 shr.u r23=in0,r20 // start / (stride size)
21 .save ar.lc, r3 34 shr.u r22=r22,r20 // (last byte address) / (stride size)
22 mov r3=ar.lc // save ar.lc 35 shl r21=r21,r20 // r21: stride size of the i-cache(s)
36 ;;
37 sub r8=r22,r23 // number of strides - 1
38 shl r24=r23,r20 // r24: addresses for "fc.i" =
39 // "start" rounded down to stride boundary
40 .save ar.lc,r3
41 mov r3=ar.lc // save ar.lc
23 ;; 42 ;;
24 43
25 .body 44 .body
26 45 mov ar.lc=r8
27 mov ar.lc=r8
28 ;; 46 ;;
29.Loop: fc.i in0 // issuable on M2 only 47 /*
30 add in0=32,in0 48 * 32 byte aligned loop, even number of (actually 2) bundles
49 */
50.Loop: fc.i r24 // issuable on M0 only
51 add r24=r21,r24 // we flush "stride size" bytes per iteration
52 nop.i 0
31 br.cloop.sptk.few .Loop 53 br.cloop.sptk.few .Loop
32 ;; 54 ;;
33 sync.i 55 sync.i
34 ;; 56 ;;
35 srlz.i 57 srlz.i
36 ;; 58 ;;
37 mov ar.lc=r3 // restore ar.lc 59 mov ar.lc=r3 // restore ar.lc
38 br.ret.sptk.many rp 60 br.ret.sptk.many rp
39END(flush_icache_range) 61END(flush_icache_range)
diff --git a/arch/ia64/pci/pci.c b/arch/ia64/pci/pci.c
index 720a861f88be..54d9ed444e4a 100644
--- a/arch/ia64/pci/pci.c
+++ b/arch/ia64/pci/pci.c
@@ -157,6 +157,7 @@ alloc_pci_controller (int seg)
157 157
158 memset(controller, 0, sizeof(*controller)); 158 memset(controller, 0, sizeof(*controller));
159 controller->segment = seg; 159 controller->segment = seg;
160 controller->node = -1;
160 return controller; 161 return controller;
161} 162}
162 163
@@ -288,6 +289,7 @@ pci_acpi_scan_root(struct acpi_device *device, int domain, int bus)
288 unsigned int windows = 0; 289 unsigned int windows = 0;
289 struct pci_bus *pbus; 290 struct pci_bus *pbus;
290 char *name; 291 char *name;
292 int pxm;
291 293
292 controller = alloc_pci_controller(domain); 294 controller = alloc_pci_controller(domain);
293 if (!controller) 295 if (!controller)
@@ -295,10 +297,16 @@ pci_acpi_scan_root(struct acpi_device *device, int domain, int bus)
295 297
296 controller->acpi_handle = device->handle; 298 controller->acpi_handle = device->handle;
297 299
300 pxm = acpi_get_pxm(controller->acpi_handle);
301#ifdef CONFIG_NUMA
302 if (pxm >= 0)
303 controller->node = pxm_to_nid_map[pxm];
304#endif
305
298 acpi_walk_resources(device->handle, METHOD_NAME__CRS, count_window, 306 acpi_walk_resources(device->handle, METHOD_NAME__CRS, count_window,
299 &windows); 307 &windows);
300 controller->window = kmalloc(sizeof(*controller->window) * windows, 308 controller->window = kmalloc_node(sizeof(*controller->window) * windows,
301 GFP_KERNEL); 309 GFP_KERNEL, controller->node);
302 if (!controller->window) 310 if (!controller->window)
303 goto out2; 311 goto out2;
304 312
diff --git a/arch/ia64/sn/kernel/io_init.c b/arch/ia64/sn/kernel/io_init.c
index a67f39e448cb..a6649baf629a 100644
--- a/arch/ia64/sn/kernel/io_init.c
+++ b/arch/ia64/sn/kernel/io_init.c
@@ -61,7 +61,7 @@ sn_default_pci_unmap(struct pci_dev *pdev, dma_addr_t addr, int direction)
61} 61}
62 62
63static void * 63static void *
64sn_default_pci_bus_fixup(struct pcibus_bussoft *soft) 64sn_default_pci_bus_fixup(struct pcibus_bussoft *soft, struct pci_controller *controller)
65{ 65{
66 return NULL; 66 return NULL;
67} 67}
@@ -362,7 +362,7 @@ void sn_pci_controller_fixup(int segment, int busnum, struct pci_bus *bus)
362 362
363 provider_soft = NULL; 363 provider_soft = NULL;
364 if (provider->bus_fixup) 364 if (provider->bus_fixup)
365 provider_soft = (*provider->bus_fixup) (prom_bussoft_ptr); 365 provider_soft = (*provider->bus_fixup) (prom_bussoft_ptr, controller);
366 366
367 if (provider_soft == NULL) 367 if (provider_soft == NULL)
368 return; /* fixup failed or not applicable */ 368 return; /* fixup failed or not applicable */
@@ -380,6 +380,22 @@ void sn_pci_controller_fixup(int segment, int busnum, struct pci_bus *bus)
380 SN_PCIBUS_BUSSOFT(bus)->bs_xwidget_info = 380 SN_PCIBUS_BUSSOFT(bus)->bs_xwidget_info =
381 &(hubdev_info->hdi_xwidget_info[SN_PCIBUS_BUSSOFT(bus)->bs_xid]); 381 &(hubdev_info->hdi_xwidget_info[SN_PCIBUS_BUSSOFT(bus)->bs_xid]);
382 382
383 /*
384 * If the node information we obtained during the fixup phase is invalid
385 * then set controller->node to -1 (undetermined)
386 */
387 if (controller->node >= num_online_nodes()) {
388 struct pcibus_bussoft *b = SN_PCIBUS_BUSSOFT(bus);
389
390 printk(KERN_WARNING "Device ASIC=%u XID=%u PBUSNUM=%lu"
391 "L_IO=%lx L_MEM=%lx BASE=%lx\n",
392 b->bs_asic_type, b->bs_xid, b->bs_persist_busnum,
393 b->bs_legacy_io, b->bs_legacy_mem, b->bs_base);
394 printk(KERN_WARNING "on node %d but only %d nodes online."
395 "Association set to undetermined.\n",
396 controller->node, num_online_nodes());
397 controller->node = -1;
398 }
383 return; 399 return;
384 400
385error_return: 401error_return:
diff --git a/arch/ia64/sn/kernel/xpc_channel.c b/arch/ia64/sn/kernel/xpc_channel.c
index 6d02dac8056f..94698bea7be0 100644
--- a/arch/ia64/sn/kernel/xpc_channel.c
+++ b/arch/ia64/sn/kernel/xpc_channel.c
@@ -72,7 +72,7 @@ xpc_initialize_channels(struct xpc_partition *part, partid_t partid)
72enum xpc_retval 72enum xpc_retval
73xpc_setup_infrastructure(struct xpc_partition *part) 73xpc_setup_infrastructure(struct xpc_partition *part)
74{ 74{
75 int ret; 75 int ret, cpuid;
76 struct timer_list *timer; 76 struct timer_list *timer;
77 partid_t partid = XPC_PARTID(part); 77 partid_t partid = XPC_PARTID(part);
78 78
@@ -223,9 +223,9 @@ xpc_setup_infrastructure(struct xpc_partition *part)
223 xpc_vars_part[partid].openclose_args_pa = 223 xpc_vars_part[partid].openclose_args_pa =
224 __pa(part->local_openclose_args); 224 __pa(part->local_openclose_args);
225 xpc_vars_part[partid].IPI_amo_pa = __pa(part->local_IPI_amo_va); 225 xpc_vars_part[partid].IPI_amo_pa = __pa(part->local_IPI_amo_va);
226 xpc_vars_part[partid].IPI_nasid = cpuid_to_nasid(smp_processor_id()); 226 cpuid = raw_smp_processor_id(); /* any CPU in this partition will do */
227 xpc_vars_part[partid].IPI_phys_cpuid = 227 xpc_vars_part[partid].IPI_nasid = cpuid_to_nasid(cpuid);
228 cpu_physical_id(smp_processor_id()); 228 xpc_vars_part[partid].IPI_phys_cpuid = cpu_physical_id(cpuid);
229 xpc_vars_part[partid].nchannels = part->nchannels; 229 xpc_vars_part[partid].nchannels = part->nchannels;
230 xpc_vars_part[partid].magic = XPC_VP_MAGIC1; 230 xpc_vars_part[partid].magic = XPC_VP_MAGIC1;
231 231
diff --git a/arch/ia64/sn/pci/pci_dma.c b/arch/ia64/sn/pci/pci_dma.c
index a2f7a88aefbb..0e4b9ad9ef02 100644
--- a/arch/ia64/sn/pci/pci_dma.c
+++ b/arch/ia64/sn/pci/pci_dma.c
@@ -79,6 +79,7 @@ void *sn_dma_alloc_coherent(struct device *dev, size_t size,
79{ 79{
80 void *cpuaddr; 80 void *cpuaddr;
81 unsigned long phys_addr; 81 unsigned long phys_addr;
82 int node;
82 struct pci_dev *pdev = to_pci_dev(dev); 83 struct pci_dev *pdev = to_pci_dev(dev);
83 struct sn_pcibus_provider *provider = SN_PCIDEV_BUSPROVIDER(pdev); 84 struct sn_pcibus_provider *provider = SN_PCIDEV_BUSPROVIDER(pdev);
84 85
@@ -86,10 +87,19 @@ void *sn_dma_alloc_coherent(struct device *dev, size_t size,
86 87
87 /* 88 /*
88 * Allocate the memory. 89 * Allocate the memory.
89 * FIXME: We should be doing alloc_pages_node for the node closest
90 * to the PCI device.
91 */ 90 */
92 if (!(cpuaddr = (void *)__get_free_pages(GFP_ATOMIC, get_order(size)))) 91 node = pcibus_to_node(pdev->bus);
92 if (likely(node >=0)) {
93 struct page *p = alloc_pages_node(node, GFP_ATOMIC, get_order(size));
94
95 if (likely(p))
96 cpuaddr = page_address(p);
97 else
98 return NULL;
99 } else
100 cpuaddr = (void *)__get_free_pages(GFP_ATOMIC, get_order(size));
101
102 if (unlikely(!cpuaddr))
93 return NULL; 103 return NULL;
94 104
95 memset(cpuaddr, 0x0, size); 105 memset(cpuaddr, 0x0, size);
diff --git a/arch/ia64/sn/pci/pcibr/pcibr_provider.c b/arch/ia64/sn/pci/pcibr/pcibr_provider.c
index 9813da56d311..b95e928636a1 100644
--- a/arch/ia64/sn/pci/pcibr/pcibr_provider.c
+++ b/arch/ia64/sn/pci/pcibr/pcibr_provider.c
@@ -85,7 +85,7 @@ pcibr_error_intr_handler(int irq, void *arg, struct pt_regs *regs)
85} 85}
86 86
87void * 87void *
88pcibr_bus_fixup(struct pcibus_bussoft *prom_bussoft) 88pcibr_bus_fixup(struct pcibus_bussoft *prom_bussoft, struct pci_controller *controller)
89{ 89{
90 int nasid, cnode, j; 90 int nasid, cnode, j;
91 struct hubdev_info *hubdev_info; 91 struct hubdev_info *hubdev_info;
@@ -158,6 +158,14 @@ pcibr_bus_fixup(struct pcibus_bussoft *prom_bussoft)
158 memset(soft->pbi_int_ate_resource.ate, 0, 158 memset(soft->pbi_int_ate_resource.ate, 0,
159 (soft->pbi_int_ate_size * sizeof(uint64_t))); 159 (soft->pbi_int_ate_size * sizeof(uint64_t)));
160 160
161 if (prom_bussoft->bs_asic_type == PCIIO_ASIC_TYPE_TIOCP)
162 /*
163 * TIO PCI Bridge with no closest node information.
164 * FIXME: Find another way to determine the closest node
165 */
166 controller->node = -1;
167 else
168 controller->node = cnode;
161 return soft; 169 return soft;
162} 170}
163 171
diff --git a/arch/ia64/sn/pci/tioca_provider.c b/arch/ia64/sn/pci/tioca_provider.c
index 51cc4e63092c..5d76a7581465 100644
--- a/arch/ia64/sn/pci/tioca_provider.c
+++ b/arch/ia64/sn/pci/tioca_provider.c
@@ -581,7 +581,7 @@ tioca_error_intr_handler(int irq, void *arg, struct pt_regs *pt)
581 * the caller. 581 * the caller.
582 */ 582 */
583static void * 583static void *
584tioca_bus_fixup(struct pcibus_bussoft *prom_bussoft) 584tioca_bus_fixup(struct pcibus_bussoft *prom_bussoft, struct pci_controller *controller)
585{ 585{
586 struct tioca_common *tioca_common; 586 struct tioca_common *tioca_common;
587 struct tioca_kernel *tioca_kern; 587 struct tioca_kernel *tioca_kern;
@@ -646,6 +646,8 @@ tioca_bus_fixup(struct pcibus_bussoft *prom_bussoft)
646 __FUNCTION__, SGI_TIOCA_ERROR, 646 __FUNCTION__, SGI_TIOCA_ERROR,
647 (int)tioca_common->ca_common.bs_persist_busnum); 647 (int)tioca_common->ca_common.bs_persist_busnum);
648 648
649 /* Setup locality information */
650 controller->node = tioca_kern->ca_closest_node;
649 return tioca_common; 651 return tioca_common;
650} 652}
651 653