aboutsummaryrefslogtreecommitdiffstats
path: root/arch
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@g5.osdl.org>2006-06-23 01:46:28 -0400
committerLinus Torvalds <torvalds@g5.osdl.org>2006-06-23 01:46:28 -0400
commit6f3cafce0ed24372084b5648c9e8a6aacbaf9900 (patch)
treea20de49dbad477a608d1df3ce19f3eeb68417585 /arch
parent0c97f524fc16004602f97ba19c36acdcc0fb9688 (diff)
parent02916526133aebc0b3b6c486d1b0af95221033bd (diff)
Merge branch 'devel' of master.kernel.org:/home/rmk/linux-2.6-arm
* 'devel' of master.kernel.org:/home/rmk/linux-2.6-arm: (21 commits) [ARM] 3629/1: S3C24XX: fix missing bracket in regs-dsc.h [ARM] 3537/1: Rework DMA-bounce locking for finer granularity [ARM] 3601/1: i.MX/MX1 DMA error handling for signaled channels only [ARM] 3597/1: ixp4xx/nslu2: Board support for new LED subsystem [ARM] 3595/1: ixp4xx/nas100d: Board support for new LED subsystem [ARM] 3626/1: ARM EABI: fix syscall restarting [ARM] 3628/1: S3C24XX: add get_rate call to struct clk [ARM] 3627/1: S3C24XX: split s3c2410 clocks from core clocks [ARM] 3613/1: S3C2410: Add sysdev and sysclass [ARM] 3624/1: Report true modem control line states [ARM] 3620/2: ixp23xx: add uengine loader support [ARM] 3618/1: add defconfig for logicpd pxa270 card engine [ARM] 3617/1: ep93xx: fix slightly incorrect timer tick rate [ARM] 3616/1: fix timer handler wrap logic for a number of platforms [ARM] 3615/1: ixp23xx: use platform devices for physmap flash [ARM] 3614/1: ep93xx: use platform devices for physmap flash [ARM] 3621/1: fix compilation breakage for pnx4008 [ARM] 3623/1: pnx4008: move GPIO-related defines to gpio.h [ARM] 3622/1: pnx4008: remove clk_use/clk_unuse [ARM] Enable VFP to be built when non-VFP capable CPUs are selected ...
Diffstat (limited to 'arch')
-rw-r--r--arch/arm/common/Makefile1
-rw-r--r--arch/arm/common/dmabounce.c67
-rw-r--r--arch/arm/common/uengine.c58
-rw-r--r--arch/arm/configs/lpd270_defconfig963
-rw-r--r--arch/arm/kernel/entry-armv.S24
-rw-r--r--arch/arm/kernel/iwmmxt.S2
-rw-r--r--arch/arm/kernel/process.c24
-rw-r--r--arch/arm/kernel/signal.c21
-rw-r--r--arch/arm/mach-ep93xx/core.c5
-rw-r--r--arch/arm/mach-ep93xx/gesbc9312.c24
-rw-r--r--arch/arm/mach-ep93xx/ts72xx.c23
-rw-r--r--arch/arm/mach-imx/dma.c65
-rw-r--r--arch/arm/mach-ixp2000/core.c3
-rw-r--r--arch/arm/mach-ixp23xx/core.c5
-rw-r--r--arch/arm/mach-ixp23xx/espresso.c22
-rw-r--r--arch/arm/mach-ixp23xx/ixdp2351.c22
-rw-r--r--arch/arm/mach-ixp23xx/roadrunner.c22
-rw-r--r--arch/arm/mach-ixp4xx/common.c2
-rw-r--r--arch/arm/mach-ixp4xx/nas100d-setup.c41
-rw-r--r--arch/arm/mach-ixp4xx/nslu2-setup.c48
-rw-r--r--arch/arm/mach-pnx4008/clock.c129
-rw-r--r--arch/arm/mach-pnx4008/serial.c2
-rw-r--r--arch/arm/mach-s3c2410/Kconfig8
-rw-r--r--arch/arm/mach-s3c2410/Makefile4
-rw-r--r--arch/arm/mach-s3c2410/clock.c228
-rw-r--r--arch/arm/mach-s3c2410/clock.h11
-rw-r--r--arch/arm/mach-s3c2410/cpu.h1
-rw-r--r--arch/arm/mach-s3c2410/s3c2410-clock.c263
-rw-r--r--arch/arm/mach-s3c2410/s3c2410.c25
-rw-r--r--arch/arm/mach-s3c2410/s3c2410.h2
-rw-r--r--arch/arm/mach-s3c2410/s3c2440-clock.c4
-rw-r--r--arch/arm/mach-s3c2410/s3c2442-clock.c2
-rw-r--r--arch/arm/mach-s3c2410/s3c244x.c2
-rw-r--r--arch/arm/nwfpe/fpmodule.c25
-rw-r--r--arch/arm/plat-omap/timer32k.c3
-rw-r--r--arch/arm/vfp/Makefile5
-rw-r--r--arch/arm/vfp/vfphw.S4
-rw-r--r--arch/arm/vfp/vfpmodule.c71
38 files changed, 1771 insertions, 460 deletions
diff --git a/arch/arm/common/Makefile b/arch/arm/common/Makefile
index 847e3e6356c6..e1289a256ce5 100644
--- a/arch/arm/common/Makefile
+++ b/arch/arm/common/Makefile
@@ -16,3 +16,4 @@ obj-$(CONFIG_SHARP_PARAM) += sharpsl_param.o
16obj-$(CONFIG_SHARPSL_PM) += sharpsl_pm.o 16obj-$(CONFIG_SHARPSL_PM) += sharpsl_pm.o
17obj-$(CONFIG_SHARP_SCOOP) += scoop.o 17obj-$(CONFIG_SHARP_SCOOP) += scoop.o
18obj-$(CONFIG_ARCH_IXP2000) += uengine.o 18obj-$(CONFIG_ARCH_IXP2000) += uengine.o
19obj-$(CONFIG_ARCH_IXP23XX) += uengine.o
diff --git a/arch/arm/common/dmabounce.c b/arch/arm/common/dmabounce.c
index 7971d0dc6892..5b7c26395b44 100644
--- a/arch/arm/common/dmabounce.c
+++ b/arch/arm/common/dmabounce.c
@@ -77,6 +77,8 @@ struct dmabounce_device_info {
77#endif 77#endif
78 struct dmabounce_pool small; 78 struct dmabounce_pool small;
79 struct dmabounce_pool large; 79 struct dmabounce_pool large;
80
81 rwlock_t lock;
80}; 82};
81 83
82static LIST_HEAD(dmabounce_devs); 84static LIST_HEAD(dmabounce_devs);
@@ -116,6 +118,7 @@ alloc_safe_buffer(struct dmabounce_device_info *device_info, void *ptr,
116 struct safe_buffer *buf; 118 struct safe_buffer *buf;
117 struct dmabounce_pool *pool; 119 struct dmabounce_pool *pool;
118 struct device *dev = device_info->dev; 120 struct device *dev = device_info->dev;
121 unsigned long flags;
119 122
120 dev_dbg(dev, "%s(ptr=%p, size=%d, dir=%d)\n", 123 dev_dbg(dev, "%s(ptr=%p, size=%d, dir=%d)\n",
121 __func__, ptr, size, dir); 124 __func__, ptr, size, dir);
@@ -163,8 +166,12 @@ alloc_safe_buffer(struct dmabounce_device_info *device_info, void *ptr,
163 print_alloc_stats(device_info); 166 print_alloc_stats(device_info);
164#endif 167#endif
165 168
169 write_lock_irqsave(&device_info->lock, flags);
170
166 list_add(&buf->node, &device_info->safe_buffers); 171 list_add(&buf->node, &device_info->safe_buffers);
167 172
173 write_unlock_irqrestore(&device_info->lock, flags);
174
168 return buf; 175 return buf;
169} 176}
170 177
@@ -172,22 +179,32 @@ alloc_safe_buffer(struct dmabounce_device_info *device_info, void *ptr,
172static inline struct safe_buffer * 179static inline struct safe_buffer *
173find_safe_buffer(struct dmabounce_device_info *device_info, dma_addr_t safe_dma_addr) 180find_safe_buffer(struct dmabounce_device_info *device_info, dma_addr_t safe_dma_addr)
174{ 181{
175 struct safe_buffer *b; 182 struct safe_buffer *b = NULL;
183 unsigned long flags;
184
185 read_lock_irqsave(&device_info->lock, flags);
176 186
177 list_for_each_entry(b, &device_info->safe_buffers, node) 187 list_for_each_entry(b, &device_info->safe_buffers, node)
178 if (b->safe_dma_addr == safe_dma_addr) 188 if (b->safe_dma_addr == safe_dma_addr)
179 return b; 189 break;
180 190
181 return NULL; 191 read_unlock_irqrestore(&device_info->lock, flags);
192 return b;
182} 193}
183 194
184static inline void 195static inline void
185free_safe_buffer(struct dmabounce_device_info *device_info, struct safe_buffer *buf) 196free_safe_buffer(struct dmabounce_device_info *device_info, struct safe_buffer *buf)
186{ 197{
198 unsigned long flags;
199
187 dev_dbg(device_info->dev, "%s(buf=%p)\n", __func__, buf); 200 dev_dbg(device_info->dev, "%s(buf=%p)\n", __func__, buf);
188 201
202 write_lock_irqsave(&device_info->lock, flags);
203
189 list_del(&buf->node); 204 list_del(&buf->node);
190 205
206 write_unlock_irqrestore(&device_info->lock, flags);
207
191 if (buf->pool) 208 if (buf->pool)
192 dma_pool_free(buf->pool->pool, buf->safe, buf->safe_dma_addr); 209 dma_pool_free(buf->pool->pool, buf->safe, buf->safe_dma_addr);
193 else 210 else
@@ -396,7 +413,6 @@ dma_addr_t
396dma_map_single(struct device *dev, void *ptr, size_t size, 413dma_map_single(struct device *dev, void *ptr, size_t size,
397 enum dma_data_direction dir) 414 enum dma_data_direction dir)
398{ 415{
399 unsigned long flags;
400 dma_addr_t dma_addr; 416 dma_addr_t dma_addr;
401 417
402 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n", 418 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n",
@@ -404,12 +420,8 @@ dma_map_single(struct device *dev, void *ptr, size_t size,
404 420
405 BUG_ON(dir == DMA_NONE); 421 BUG_ON(dir == DMA_NONE);
406 422
407 local_irq_save(flags);
408
409 dma_addr = map_single(dev, ptr, size, dir); 423 dma_addr = map_single(dev, ptr, size, dir);
410 424
411 local_irq_restore(flags);
412
413 return dma_addr; 425 return dma_addr;
414} 426}
415 427
@@ -424,25 +436,18 @@ void
424dma_unmap_single(struct device *dev, dma_addr_t dma_addr, size_t size, 436dma_unmap_single(struct device *dev, dma_addr_t dma_addr, size_t size,
425 enum dma_data_direction dir) 437 enum dma_data_direction dir)
426{ 438{
427 unsigned long flags;
428
429 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n", 439 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n",
430 __func__, (void *) dma_addr, size, dir); 440 __func__, (void *) dma_addr, size, dir);
431 441
432 BUG_ON(dir == DMA_NONE); 442 BUG_ON(dir == DMA_NONE);
433 443
434 local_irq_save(flags);
435
436 unmap_single(dev, dma_addr, size, dir); 444 unmap_single(dev, dma_addr, size, dir);
437
438 local_irq_restore(flags);
439} 445}
440 446
441int 447int
442dma_map_sg(struct device *dev, struct scatterlist *sg, int nents, 448dma_map_sg(struct device *dev, struct scatterlist *sg, int nents,
443 enum dma_data_direction dir) 449 enum dma_data_direction dir)
444{ 450{
445 unsigned long flags;
446 int i; 451 int i;
447 452
448 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n", 453 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n",
@@ -450,8 +455,6 @@ dma_map_sg(struct device *dev, struct scatterlist *sg, int nents,
450 455
451 BUG_ON(dir == DMA_NONE); 456 BUG_ON(dir == DMA_NONE);
452 457
453 local_irq_save(flags);
454
455 for (i = 0; i < nents; i++, sg++) { 458 for (i = 0; i < nents; i++, sg++) {
456 struct page *page = sg->page; 459 struct page *page = sg->page;
457 unsigned int offset = sg->offset; 460 unsigned int offset = sg->offset;
@@ -462,8 +465,6 @@ dma_map_sg(struct device *dev, struct scatterlist *sg, int nents,
462 map_single(dev, ptr, length, dir); 465 map_single(dev, ptr, length, dir);
463 } 466 }
464 467
465 local_irq_restore(flags);
466
467 return nents; 468 return nents;
468} 469}
469 470
@@ -471,7 +472,6 @@ void
471dma_unmap_sg(struct device *dev, struct scatterlist *sg, int nents, 472dma_unmap_sg(struct device *dev, struct scatterlist *sg, int nents,
472 enum dma_data_direction dir) 473 enum dma_data_direction dir)
473{ 474{
474 unsigned long flags;
475 int i; 475 int i;
476 476
477 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n", 477 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n",
@@ -479,55 +479,38 @@ dma_unmap_sg(struct device *dev, struct scatterlist *sg, int nents,
479 479
480 BUG_ON(dir == DMA_NONE); 480 BUG_ON(dir == DMA_NONE);
481 481
482 local_irq_save(flags);
483
484 for (i = 0; i < nents; i++, sg++) { 482 for (i = 0; i < nents; i++, sg++) {
485 dma_addr_t dma_addr = sg->dma_address; 483 dma_addr_t dma_addr = sg->dma_address;
486 unsigned int length = sg->length; 484 unsigned int length = sg->length;
487 485
488 unmap_single(dev, dma_addr, length, dir); 486 unmap_single(dev, dma_addr, length, dir);
489 } 487 }
490
491 local_irq_restore(flags);
492} 488}
493 489
494void 490void
495dma_sync_single_for_cpu(struct device *dev, dma_addr_t dma_addr, size_t size, 491dma_sync_single_for_cpu(struct device *dev, dma_addr_t dma_addr, size_t size,
496 enum dma_data_direction dir) 492 enum dma_data_direction dir)
497{ 493{
498 unsigned long flags;
499
500 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n", 494 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n",
501 __func__, (void *) dma_addr, size, dir); 495 __func__, (void *) dma_addr, size, dir);
502 496
503 local_irq_save(flags);
504
505 sync_single(dev, dma_addr, size, dir); 497 sync_single(dev, dma_addr, size, dir);
506
507 local_irq_restore(flags);
508} 498}
509 499
510void 500void
511dma_sync_single_for_device(struct device *dev, dma_addr_t dma_addr, size_t size, 501dma_sync_single_for_device(struct device *dev, dma_addr_t dma_addr, size_t size,
512 enum dma_data_direction dir) 502 enum dma_data_direction dir)
513{ 503{
514 unsigned long flags;
515
516 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n", 504 dev_dbg(dev, "%s(ptr=%p,size=%d,dir=%x)\n",
517 __func__, (void *) dma_addr, size, dir); 505 __func__, (void *) dma_addr, size, dir);
518 506
519 local_irq_save(flags);
520
521 sync_single(dev, dma_addr, size, dir); 507 sync_single(dev, dma_addr, size, dir);
522
523 local_irq_restore(flags);
524} 508}
525 509
526void 510void
527dma_sync_sg_for_cpu(struct device *dev, struct scatterlist *sg, int nents, 511dma_sync_sg_for_cpu(struct device *dev, struct scatterlist *sg, int nents,
528 enum dma_data_direction dir) 512 enum dma_data_direction dir)
529{ 513{
530 unsigned long flags;
531 int i; 514 int i;
532 515
533 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n", 516 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n",
@@ -535,23 +518,18 @@ dma_sync_sg_for_cpu(struct device *dev, struct scatterlist *sg, int nents,
535 518
536 BUG_ON(dir == DMA_NONE); 519 BUG_ON(dir == DMA_NONE);
537 520
538 local_irq_save(flags);
539
540 for (i = 0; i < nents; i++, sg++) { 521 for (i = 0; i < nents; i++, sg++) {
541 dma_addr_t dma_addr = sg->dma_address; 522 dma_addr_t dma_addr = sg->dma_address;
542 unsigned int length = sg->length; 523 unsigned int length = sg->length;
543 524
544 sync_single(dev, dma_addr, length, dir); 525 sync_single(dev, dma_addr, length, dir);
545 } 526 }
546
547 local_irq_restore(flags);
548} 527}
549 528
550void 529void
551dma_sync_sg_for_device(struct device *dev, struct scatterlist *sg, int nents, 530dma_sync_sg_for_device(struct device *dev, struct scatterlist *sg, int nents,
552 enum dma_data_direction dir) 531 enum dma_data_direction dir)
553{ 532{
554 unsigned long flags;
555 int i; 533 int i;
556 534
557 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n", 535 dev_dbg(dev, "%s(sg=%p,nents=%d,dir=%x)\n",
@@ -559,16 +537,12 @@ dma_sync_sg_for_device(struct device *dev, struct scatterlist *sg, int nents,
559 537
560 BUG_ON(dir == DMA_NONE); 538 BUG_ON(dir == DMA_NONE);
561 539
562 local_irq_save(flags);
563
564 for (i = 0; i < nents; i++, sg++) { 540 for (i = 0; i < nents; i++, sg++) {
565 dma_addr_t dma_addr = sg->dma_address; 541 dma_addr_t dma_addr = sg->dma_address;
566 unsigned int length = sg->length; 542 unsigned int length = sg->length;
567 543
568 sync_single(dev, dma_addr, length, dir); 544 sync_single(dev, dma_addr, length, dir);
569 } 545 }
570
571 local_irq_restore(flags);
572} 546}
573 547
574static int 548static int
@@ -622,6 +596,7 @@ dmabounce_register_dev(struct device *dev, unsigned long small_buffer_size,
622 596
623 device_info->dev = dev; 597 device_info->dev = dev;
624 INIT_LIST_HEAD(&device_info->safe_buffers); 598 INIT_LIST_HEAD(&device_info->safe_buffers);
599 rwlock_init(&device_info->lock);
625 600
626#ifdef STATS 601#ifdef STATS
627 device_info->total_allocs = 0; 602 device_info->total_allocs = 0;
diff --git a/arch/arm/common/uengine.c b/arch/arm/common/uengine.c
index a1310b71004e..dfca596a9a27 100644
--- a/arch/arm/common/uengine.c
+++ b/arch/arm/common/uengine.c
@@ -18,10 +18,26 @@
18#include <linux/module.h> 18#include <linux/module.h>
19#include <linux/string.h> 19#include <linux/string.h>
20#include <asm/hardware.h> 20#include <asm/hardware.h>
21#include <asm/arch/ixp2000-regs.h> 21#include <asm/arch/hardware.h>
22#include <asm/hardware/uengine.h> 22#include <asm/hardware/uengine.h>
23#include <asm/io.h> 23#include <asm/io.h>
24 24
25#if defined(CONFIG_ARCH_IXP2000)
26#define IXP_UENGINE_CSR_VIRT_BASE IXP2000_UENGINE_CSR_VIRT_BASE
27#define IXP_PRODUCT_ID IXP2000_PRODUCT_ID
28#define IXP_MISC_CONTROL IXP2000_MISC_CONTROL
29#define IXP_RESET1 IXP2000_RESET1
30#else
31#if defined(CONFIG_ARCH_IXP23XX)
32#define IXP_UENGINE_CSR_VIRT_BASE IXP23XX_UENGINE_CSR_VIRT_BASE
33#define IXP_PRODUCT_ID IXP23XX_PRODUCT_ID
34#define IXP_MISC_CONTROL IXP23XX_MISC_CONTROL
35#define IXP_RESET1 IXP23XX_RESET1
36#else
37#error unknown platform
38#endif
39#endif
40
25#define USTORE_ADDRESS 0x000 41#define USTORE_ADDRESS 0x000
26#define USTORE_DATA_LOWER 0x004 42#define USTORE_DATA_LOWER 0x004
27#define USTORE_DATA_UPPER 0x008 43#define USTORE_DATA_UPPER 0x008
@@ -43,7 +59,7 @@ u32 ixp2000_uengine_mask;
43 59
44static void *ixp2000_uengine_csr_area(int uengine) 60static void *ixp2000_uengine_csr_area(int uengine)
45{ 61{
46 return ((void *)IXP2000_UENGINE_CSR_VIRT_BASE) + (uengine << 10); 62 return ((void *)IXP_UENGINE_CSR_VIRT_BASE) + (uengine << 10);
47} 63}
48 64
49/* 65/*
@@ -91,8 +107,13 @@ EXPORT_SYMBOL(ixp2000_uengine_csr_write);
91 107
92void ixp2000_uengine_reset(u32 uengine_mask) 108void ixp2000_uengine_reset(u32 uengine_mask)
93{ 109{
94 ixp2000_reg_wrb(IXP2000_RESET1, uengine_mask & ixp2000_uengine_mask); 110 u32 value;
95 ixp2000_reg_wrb(IXP2000_RESET1, 0); 111
112 value = ixp2000_reg_read(IXP_RESET1) & ~ixp2000_uengine_mask;
113
114 uengine_mask &= ixp2000_uengine_mask;
115 ixp2000_reg_wrb(IXP_RESET1, value | uengine_mask);
116 ixp2000_reg_wrb(IXP_RESET1, value);
96} 117}
97EXPORT_SYMBOL(ixp2000_uengine_reset); 118EXPORT_SYMBOL(ixp2000_uengine_reset);
98 119
@@ -235,11 +256,12 @@ static int check_ixp_type(struct ixp2000_uengine_code *c)
235 u32 product_id; 256 u32 product_id;
236 u32 rev; 257 u32 rev;
237 258
238 product_id = ixp2000_reg_read(IXP2000_PRODUCT_ID); 259 product_id = ixp2000_reg_read(IXP_PRODUCT_ID);
239 if (((product_id >> 16) & 0x1f) != 0) 260 if (((product_id >> 16) & 0x1f) != 0)
240 return 0; 261 return 0;
241 262
242 switch ((product_id >> 8) & 0xff) { 263 switch ((product_id >> 8) & 0xff) {
264#ifdef CONFIG_ARCH_IXP2000
243 case 0: /* IXP2800 */ 265 case 0: /* IXP2800 */
244 if (!(c->cpu_model_bitmask & 4)) 266 if (!(c->cpu_model_bitmask & 4))
245 return 0; 267 return 0;
@@ -254,6 +276,14 @@ static int check_ixp_type(struct ixp2000_uengine_code *c)
254 if (!(c->cpu_model_bitmask & 2)) 276 if (!(c->cpu_model_bitmask & 2))
255 return 0; 277 return 0;
256 break; 278 break;
279#endif
280
281#ifdef CONFIG_ARCH_IXP23XX
282 case 4: /* IXP23xx */
283 if (!(c->cpu_model_bitmask & 0x3f0))
284 return 0;
285 break;
286#endif
257 287
258 default: 288 default:
259 return 0; 289 return 0;
@@ -432,7 +462,8 @@ static int __init ixp2000_uengine_init(void)
432 /* 462 /*
433 * Determine number of microengines present. 463 * Determine number of microengines present.
434 */ 464 */
435 switch ((ixp2000_reg_read(IXP2000_PRODUCT_ID) >> 8) & 0x1fff) { 465 switch ((ixp2000_reg_read(IXP_PRODUCT_ID) >> 8) & 0x1fff) {
466#ifdef CONFIG_ARCH_IXP2000
436 case 0: /* IXP2800 */ 467 case 0: /* IXP2800 */
437 case 1: /* IXP2850 */ 468 case 1: /* IXP2850 */
438 ixp2000_uengine_mask = 0x00ff00ff; 469 ixp2000_uengine_mask = 0x00ff00ff;
@@ -441,10 +472,17 @@ static int __init ixp2000_uengine_init(void)
441 case 2: /* IXP2400 */ 472 case 2: /* IXP2400 */
442 ixp2000_uengine_mask = 0x000f000f; 473 ixp2000_uengine_mask = 0x000f000f;
443 break; 474 break;
475#endif
476
477#ifdef CONFIG_ARCH_IXP23XX
478 case 4: /* IXP23xx */
479 ixp2000_uengine_mask = (*IXP23XX_EXP_CFG_FUSE >> 8) & 0xf;
480 break;
481#endif
444 482
445 default: 483 default:
446 printk(KERN_INFO "Detected unknown IXP2000 model (%.8x)\n", 484 printk(KERN_INFO "Detected unknown IXP2000 model (%.8x)\n",
447 (unsigned int)ixp2000_reg_read(IXP2000_PRODUCT_ID)); 485 (unsigned int)ixp2000_reg_read(IXP_PRODUCT_ID));
448 ixp2000_uengine_mask = 0x00000000; 486 ixp2000_uengine_mask = 0x00000000;
449 break; 487 break;
450 } 488 }
@@ -457,15 +495,15 @@ static int __init ixp2000_uengine_init(void)
457 /* 495 /*
458 * Synchronise timestamp counters across all microengines. 496 * Synchronise timestamp counters across all microengines.
459 */ 497 */
460 value = ixp2000_reg_read(IXP2000_MISC_CONTROL); 498 value = ixp2000_reg_read(IXP_MISC_CONTROL);
461 ixp2000_reg_wrb(IXP2000_MISC_CONTROL, value & ~0x80); 499 ixp2000_reg_wrb(IXP_MISC_CONTROL, value & ~0x80);
462 for (uengine = 0; uengine < 32; uengine++) { 500 for (uengine = 0; uengine < 32; uengine++) {
463 if (ixp2000_uengine_mask & (1 << uengine)) { 501 if (ixp2000_uengine_mask & (1 << uengine)) {
464 ixp2000_uengine_csr_write(uengine, TIMESTAMP_LOW, 0); 502 ixp2000_uengine_csr_write(uengine, TIMESTAMP_LOW, 0);
465 ixp2000_uengine_csr_write(uengine, TIMESTAMP_HIGH, 0); 503 ixp2000_uengine_csr_write(uengine, TIMESTAMP_HIGH, 0);
466 } 504 }
467 } 505 }
468 ixp2000_reg_wrb(IXP2000_MISC_CONTROL, value | 0x80); 506 ixp2000_reg_wrb(IXP_MISC_CONTROL, value | 0x80);
469 507
470 return 0; 508 return 0;
471} 509}
diff --git a/arch/arm/configs/lpd270_defconfig b/arch/arm/configs/lpd270_defconfig
new file mode 100644
index 000000000000..d08bbe59483a
--- /dev/null
+++ b/arch/arm/configs/lpd270_defconfig
@@ -0,0 +1,963 @@
1#
2# Automatically generated make config: don't edit
3# Linux kernel version: 2.6.17-git2
4# Wed Jun 21 22:20:18 2006
5#
6CONFIG_ARM=y
7CONFIG_MMU=y
8CONFIG_RWSEM_GENERIC_SPINLOCK=y
9CONFIG_GENERIC_HWEIGHT=y
10CONFIG_GENERIC_CALIBRATE_DELAY=y
11CONFIG_ARCH_MTD_XIP=y
12CONFIG_VECTORS_BASE=0xffff0000
13
14#
15# Code maturity level options
16#
17CONFIG_EXPERIMENTAL=y
18CONFIG_BROKEN_ON_SMP=y
19CONFIG_INIT_ENV_ARG_LIMIT=32
20
21#
22# General setup
23#
24CONFIG_LOCALVERSION=""
25CONFIG_LOCALVERSION_AUTO=y
26CONFIG_SWAP=y
27CONFIG_SYSVIPC=y
28# CONFIG_POSIX_MQUEUE is not set
29# CONFIG_BSD_PROCESS_ACCT is not set
30CONFIG_SYSCTL=y
31# CONFIG_AUDIT is not set
32# CONFIG_IKCONFIG is not set
33# CONFIG_RELAY is not set
34CONFIG_INITRAMFS_SOURCE=""
35CONFIG_UID16=y
36CONFIG_CC_OPTIMIZE_FOR_SIZE=y
37# CONFIG_EMBEDDED is not set
38CONFIG_KALLSYMS=y
39# CONFIG_KALLSYMS_ALL is not set
40# CONFIG_KALLSYMS_EXTRA_PASS is not set
41CONFIG_HOTPLUG=y
42CONFIG_PRINTK=y
43CONFIG_BUG=y
44CONFIG_ELF_CORE=y
45CONFIG_BASE_FULL=y
46CONFIG_FUTEX=y
47CONFIG_EPOLL=y
48CONFIG_SHMEM=y
49CONFIG_SLAB=y
50# CONFIG_TINY_SHMEM is not set
51CONFIG_BASE_SMALL=0
52# CONFIG_SLOB is not set
53
54#
55# Loadable module support
56#
57CONFIG_MODULES=y
58# CONFIG_MODULE_UNLOAD is not set
59# CONFIG_MODVERSIONS is not set
60# CONFIG_MODULE_SRCVERSION_ALL is not set
61# CONFIG_KMOD is not set
62
63#
64# Block layer
65#
66# CONFIG_BLK_DEV_IO_TRACE is not set
67
68#
69# IO Schedulers
70#
71CONFIG_IOSCHED_NOOP=y
72CONFIG_IOSCHED_AS=y
73CONFIG_IOSCHED_DEADLINE=y
74CONFIG_IOSCHED_CFQ=y
75CONFIG_DEFAULT_AS=y
76# CONFIG_DEFAULT_DEADLINE is not set
77# CONFIG_DEFAULT_CFQ is not set
78# CONFIG_DEFAULT_NOOP is not set
79CONFIG_DEFAULT_IOSCHED="anticipatory"
80
81#
82# System Type
83#
84# CONFIG_ARCH_AAEC2000 is not set
85# CONFIG_ARCH_INTEGRATOR is not set
86# CONFIG_ARCH_REALVIEW is not set
87# CONFIG_ARCH_VERSATILE is not set
88# CONFIG_ARCH_AT91RM9200 is not set
89# CONFIG_ARCH_CLPS7500 is not set
90# CONFIG_ARCH_CLPS711X is not set
91# CONFIG_ARCH_CO285 is not set
92# CONFIG_ARCH_EBSA110 is not set
93# CONFIG_ARCH_EP93XX is not set
94# CONFIG_ARCH_FOOTBRIDGE is not set
95# CONFIG_ARCH_NETX is not set
96# CONFIG_ARCH_H720X is not set
97# CONFIG_ARCH_IMX is not set
98# CONFIG_ARCH_IOP3XX is not set
99# CONFIG_ARCH_IXP4XX is not set
100# CONFIG_ARCH_IXP2000 is not set
101# CONFIG_ARCH_IXP23XX is not set
102# CONFIG_ARCH_L7200 is not set
103# CONFIG_ARCH_PNX4008 is not set
104CONFIG_ARCH_PXA=y
105# CONFIG_ARCH_RPC is not set
106# CONFIG_ARCH_SA1100 is not set
107# CONFIG_ARCH_S3C2410 is not set
108# CONFIG_ARCH_SHARK is not set
109# CONFIG_ARCH_LH7A40X is not set
110# CONFIG_ARCH_OMAP is not set
111
112#
113# Intel PXA2xx Implementations
114#
115# CONFIG_ARCH_LUBBOCK is not set
116CONFIG_MACH_LOGICPD_PXA270=y
117# CONFIG_MACH_MAINSTONE is not set
118# CONFIG_ARCH_PXA_IDP is not set
119# CONFIG_PXA_SHARPSL is not set
120CONFIG_PXA27x=y
121CONFIG_IWMMXT=y
122
123#
124# Processor Type
125#
126CONFIG_CPU_32=y
127CONFIG_CPU_XSCALE=y
128CONFIG_CPU_32v5=y
129CONFIG_CPU_ABRT_EV5T=y
130CONFIG_CPU_CACHE_VIVT=y
131CONFIG_CPU_TLB_V4WBI=y
132
133#
134# Processor Features
135#
136# CONFIG_ARM_THUMB is not set
137CONFIG_XSCALE_PMU=y
138
139#
140# Bus support
141#
142
143#
144# PCCARD (PCMCIA/CardBus) support
145#
146# CONFIG_PCCARD is not set
147
148#
149# Kernel Features
150#
151# CONFIG_PREEMPT is not set
152# CONFIG_NO_IDLE_HZ is not set
153CONFIG_HZ=100
154# CONFIG_AEABI is not set
155# CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set
156CONFIG_SELECT_MEMORY_MODEL=y
157CONFIG_FLATMEM_MANUAL=y
158# CONFIG_DISCONTIGMEM_MANUAL is not set
159# CONFIG_SPARSEMEM_MANUAL is not set
160CONFIG_FLATMEM=y
161CONFIG_FLAT_NODE_MEM_MAP=y
162# CONFIG_SPARSEMEM_STATIC is not set
163CONFIG_SPLIT_PTLOCK_CPUS=4096
164CONFIG_ALIGNMENT_TRAP=y
165
166#
167# Boot options
168#
169CONFIG_ZBOOT_ROM_TEXT=0x0
170CONFIG_ZBOOT_ROM_BSS=0x0
171CONFIG_CMDLINE="root=/dev/nfs ip=bootp console=ttyS0,115200 mem=64M"
172# CONFIG_XIP_KERNEL is not set
173
174#
175# Floating point emulation
176#
177
178#
179# At least one emulation must be selected
180#
181CONFIG_FPE_NWFPE=y
182# CONFIG_FPE_NWFPE_XP is not set
183# CONFIG_FPE_FASTFPE is not set
184
185#
186# Userspace binary formats
187#
188CONFIG_BINFMT_ELF=y
189# CONFIG_BINFMT_AOUT is not set
190# CONFIG_BINFMT_MISC is not set
191# CONFIG_ARTHUR is not set
192
193#
194# Power management options
195#
196# CONFIG_PM is not set
197# CONFIG_PM_LEGACY is not set
198# CONFIG_PM_DEBUG is not set
199# CONFIG_APM is not set
200
201#
202# Networking
203#
204CONFIG_NET=y
205
206#
207# Networking options
208#
209# CONFIG_NETDEBUG is not set
210# CONFIG_PACKET is not set
211CONFIG_UNIX=y
212CONFIG_XFRM=y
213# CONFIG_XFRM_USER is not set
214# CONFIG_NET_KEY is not set
215CONFIG_INET=y
216# CONFIG_IP_MULTICAST is not set
217# CONFIG_IP_ADVANCED_ROUTER is not set
218CONFIG_IP_FIB_HASH=y
219CONFIG_IP_PNP=y
220# CONFIG_IP_PNP_DHCP is not set
221CONFIG_IP_PNP_BOOTP=y
222# CONFIG_IP_PNP_RARP is not set
223# CONFIG_NET_IPIP is not set
224# CONFIG_NET_IPGRE is not set
225# CONFIG_ARPD is not set
226# CONFIG_SYN_COOKIES is not set
227# CONFIG_INET_AH is not set
228# CONFIG_INET_ESP is not set
229# CONFIG_INET_IPCOMP is not set
230# CONFIG_INET_XFRM_TUNNEL is not set
231# CONFIG_INET_TUNNEL is not set
232CONFIG_INET_XFRM_MODE_TRANSPORT=y
233CONFIG_INET_XFRM_MODE_TUNNEL=y
234CONFIG_INET_DIAG=y
235CONFIG_INET_TCP_DIAG=y
236# CONFIG_TCP_CONG_ADVANCED is not set
237CONFIG_TCP_CONG_BIC=y
238# CONFIG_IPV6 is not set
239# CONFIG_INET6_XFRM_TUNNEL is not set
240# CONFIG_INET6_TUNNEL is not set
241# CONFIG_NETWORK_SECMARK is not set
242# CONFIG_NETFILTER is not set
243
244#
245# DCCP Configuration (EXPERIMENTAL)
246#
247# CONFIG_IP_DCCP is not set
248
249#
250# SCTP Configuration (EXPERIMENTAL)
251#
252# CONFIG_IP_SCTP is not set
253
254#
255# TIPC Configuration (EXPERIMENTAL)
256#
257# CONFIG_TIPC is not set
258# CONFIG_ATM is not set
259# CONFIG_BRIDGE is not set
260# CONFIG_VLAN_8021Q is not set
261# CONFIG_DECNET is not set
262# CONFIG_LLC2 is not set
263# CONFIG_IPX is not set
264# CONFIG_ATALK is not set
265# CONFIG_X25 is not set
266# CONFIG_LAPB is not set
267# CONFIG_NET_DIVERT is not set
268# CONFIG_ECONET is not set
269# CONFIG_WAN_ROUTER is not set
270
271#
272# QoS and/or fair queueing
273#
274# CONFIG_NET_SCHED is not set
275
276#
277# Network testing
278#
279# CONFIG_NET_PKTGEN is not set
280# CONFIG_HAMRADIO is not set
281# CONFIG_IRDA is not set
282# CONFIG_BT is not set
283# CONFIG_IEEE80211 is not set
284
285#
286# Device Drivers
287#
288
289#
290# Generic Driver Options
291#
292CONFIG_STANDALONE=y
293CONFIG_PREVENT_FIRMWARE_BUILD=y
294# CONFIG_FW_LOADER is not set
295# CONFIG_DEBUG_DRIVER is not set
296
297#
298# Connector - unified userspace <-> kernelspace linker
299#
300# CONFIG_CONNECTOR is not set
301
302#
303# Memory Technology Devices (MTD)
304#
305CONFIG_MTD=y
306# CONFIG_MTD_DEBUG is not set
307# CONFIG_MTD_CONCAT is not set
308CONFIG_MTD_PARTITIONS=y
309CONFIG_MTD_REDBOOT_PARTS=y
310CONFIG_MTD_REDBOOT_DIRECTORY_BLOCK=-1
311# CONFIG_MTD_REDBOOT_PARTS_UNALLOCATED is not set
312# CONFIG_MTD_REDBOOT_PARTS_READONLY is not set
313# CONFIG_MTD_CMDLINE_PARTS is not set
314# CONFIG_MTD_AFS_PARTS is not set
315
316#
317# User Modules And Translation Layers
318#
319CONFIG_MTD_CHAR=y
320CONFIG_MTD_BLOCK=y
321# CONFIG_FTL is not set
322# CONFIG_NFTL is not set
323# CONFIG_INFTL is not set
324# CONFIG_RFD_FTL is not set
325
326#
327# RAM/ROM/Flash chip drivers
328#
329CONFIG_MTD_CFI=y
330# CONFIG_MTD_JEDECPROBE is not set
331CONFIG_MTD_GEN_PROBE=y
332CONFIG_MTD_CFI_ADV_OPTIONS=y
333CONFIG_MTD_CFI_NOSWAP=y
334# CONFIG_MTD_CFI_BE_BYTE_SWAP is not set
335# CONFIG_MTD_CFI_LE_BYTE_SWAP is not set
336CONFIG_MTD_CFI_GEOMETRY=y
337CONFIG_MTD_MAP_BANK_WIDTH_1=y
338CONFIG_MTD_MAP_BANK_WIDTH_2=y
339CONFIG_MTD_MAP_BANK_WIDTH_4=y
340# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set
341# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set
342# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set
343# CONFIG_MTD_CFI_I1 is not set
344CONFIG_MTD_CFI_I2=y
345# CONFIG_MTD_CFI_I4 is not set
346# CONFIG_MTD_CFI_I8 is not set
347# CONFIG_MTD_OTP is not set
348CONFIG_MTD_CFI_INTELEXT=y
349# CONFIG_MTD_CFI_AMDSTD is not set
350# CONFIG_MTD_CFI_STAA is not set
351CONFIG_MTD_CFI_UTIL=y
352# CONFIG_MTD_RAM is not set
353# CONFIG_MTD_ROM is not set
354# CONFIG_MTD_ABSENT is not set
355# CONFIG_MTD_OBSOLETE_CHIPS is not set
356# CONFIG_MTD_XIP is not set
357
358#
359# Mapping drivers for chip access
360#
361# CONFIG_MTD_COMPLEX_MAPPINGS is not set
362# CONFIG_MTD_PHYSMAP is not set
363# CONFIG_MTD_ARM_INTEGRATOR is not set
364# CONFIG_MTD_SHARP_SL is not set
365# CONFIG_MTD_PLATRAM is not set
366
367#
368# Self-contained MTD device drivers
369#
370# CONFIG_MTD_SLRAM is not set
371# CONFIG_MTD_PHRAM is not set
372# CONFIG_MTD_MTDRAM is not set
373# CONFIG_MTD_BLOCK2MTD is not set
374
375#
376# Disk-On-Chip Device Drivers
377#
378# CONFIG_MTD_DOC2000 is not set
379# CONFIG_MTD_DOC2001 is not set
380# CONFIG_MTD_DOC2001PLUS is not set
381
382#
383# NAND Flash Device Drivers
384#
385# CONFIG_MTD_NAND is not set
386
387#
388# OneNAND Flash Device Drivers
389#
390# CONFIG_MTD_ONENAND is not set
391
392#
393# Parallel port support
394#
395# CONFIG_PARPORT is not set
396
397#
398# Plug and Play support
399#
400
401#
402# Block devices
403#
404# CONFIG_BLK_DEV_COW_COMMON is not set
405# CONFIG_BLK_DEV_LOOP is not set
406# CONFIG_BLK_DEV_NBD is not set
407# CONFIG_BLK_DEV_RAM is not set
408# CONFIG_BLK_DEV_INITRD is not set
409# CONFIG_CDROM_PKTCDVD is not set
410# CONFIG_ATA_OVER_ETH is not set
411
412#
413# ATA/ATAPI/MFM/RLL support
414#
415CONFIG_IDE=y
416CONFIG_BLK_DEV_IDE=y
417
418#
419# Please see Documentation/ide.txt for help/info on IDE drives
420#
421# CONFIG_BLK_DEV_IDE_SATA is not set
422CONFIG_BLK_DEV_IDEDISK=y
423# CONFIG_IDEDISK_MULTI_MODE is not set
424# CONFIG_BLK_DEV_IDECD is not set
425# CONFIG_BLK_DEV_IDETAPE is not set
426# CONFIG_BLK_DEV_IDEFLOPPY is not set
427# CONFIG_IDE_TASK_IOCTL is not set
428
429#
430# IDE chipset support/bugfixes
431#
432# CONFIG_IDE_GENERIC is not set
433# CONFIG_IDE_ARM is not set
434# CONFIG_BLK_DEV_IDEDMA is not set
435# CONFIG_IDEDMA_AUTO is not set
436# CONFIG_BLK_DEV_HD is not set
437
438#
439# SCSI device support
440#
441# CONFIG_RAID_ATTRS is not set
442# CONFIG_SCSI is not set
443
444#
445# Multi-device support (RAID and LVM)
446#
447# CONFIG_MD is not set
448
449#
450# Fusion MPT device support
451#
452# CONFIG_FUSION is not set
453
454#
455# IEEE 1394 (FireWire) support
456#
457
458#
459# I2O device support
460#
461
462#
463# Network device support
464#
465CONFIG_NETDEVICES=y
466# CONFIG_DUMMY is not set
467# CONFIG_BONDING is not set
468# CONFIG_EQUALIZER is not set
469# CONFIG_TUN is not set
470
471#
472# PHY device support
473#
474# CONFIG_PHYLIB is not set
475
476#
477# Ethernet (10 or 100Mbit)
478#
479CONFIG_NET_ETHERNET=y
480CONFIG_MII=y
481CONFIG_SMC91X=y
482# CONFIG_DM9000 is not set
483# CONFIG_SMC911X is not set
484
485#
486# Ethernet (1000 Mbit)
487#
488
489#
490# Ethernet (10000 Mbit)
491#
492
493#
494# Token Ring devices
495#
496
497#
498# Wireless LAN (non-hamradio)
499#
500# CONFIG_NET_RADIO is not set
501
502#
503# Wan interfaces
504#
505# CONFIG_WAN is not set
506# CONFIG_PPP is not set
507# CONFIG_SLIP is not set
508# CONFIG_SHAPER is not set
509# CONFIG_NETCONSOLE is not set
510# CONFIG_NETPOLL is not set
511# CONFIG_NET_POLL_CONTROLLER is not set
512
513#
514# ISDN subsystem
515#
516# CONFIG_ISDN is not set
517
518#
519# Input device support
520#
521CONFIG_INPUT=y
522
523#
524# Userland interfaces
525#
526CONFIG_INPUT_MOUSEDEV=y
527CONFIG_INPUT_MOUSEDEV_PSAUX=y
528CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
529CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
530# CONFIG_INPUT_JOYDEV is not set
531# CONFIG_INPUT_TSDEV is not set
532CONFIG_INPUT_EVDEV=y
533# CONFIG_INPUT_EVBUG is not set
534
535#
536# Input Device Drivers
537#
538CONFIG_INPUT_KEYBOARD=y
539CONFIG_KEYBOARD_ATKBD=y
540# CONFIG_KEYBOARD_SUNKBD is not set
541# CONFIG_KEYBOARD_LKKBD is not set
542# CONFIG_KEYBOARD_XTKBD is not set
543# CONFIG_KEYBOARD_NEWTON is not set
544# CONFIG_INPUT_MOUSE is not set
545# CONFIG_INPUT_JOYSTICK is not set
546# CONFIG_INPUT_TOUCHSCREEN is not set
547# CONFIG_INPUT_MISC is not set
548
549#
550# Hardware I/O ports
551#
552CONFIG_SERIO=y
553# CONFIG_SERIO_SERPORT is not set
554CONFIG_SERIO_LIBPS2=y
555# CONFIG_SERIO_RAW is not set
556# CONFIG_GAMEPORT is not set
557
558#
559# Character devices
560#
561CONFIG_VT=y
562CONFIG_VT_CONSOLE=y
563CONFIG_HW_CONSOLE=y
564# CONFIG_SERIAL_NONSTANDARD is not set
565
566#
567# Serial drivers
568#
569# CONFIG_SERIAL_8250 is not set
570
571#
572# Non-8250 serial port support
573#
574CONFIG_SERIAL_PXA=y
575CONFIG_SERIAL_PXA_CONSOLE=y
576CONFIG_SERIAL_CORE=y
577CONFIG_SERIAL_CORE_CONSOLE=y
578CONFIG_UNIX98_PTYS=y
579CONFIG_LEGACY_PTYS=y
580CONFIG_LEGACY_PTY_COUNT=256
581
582#
583# IPMI
584#
585# CONFIG_IPMI_HANDLER is not set
586
587#
588# Watchdog Cards
589#
590# CONFIG_WATCHDOG is not set
591# CONFIG_NVRAM is not set
592# CONFIG_DTLK is not set
593# CONFIG_R3964 is not set
594
595#
596# Ftape, the floppy tape device driver
597#
598# CONFIG_RAW_DRIVER is not set
599
600#
601# TPM devices
602#
603# CONFIG_TCG_TPM is not set
604# CONFIG_TELCLOCK is not set
605
606#
607# I2C support
608#
609# CONFIG_I2C is not set
610
611#
612# SPI support
613#
614# CONFIG_SPI is not set
615# CONFIG_SPI_MASTER is not set
616
617#
618# Dallas's 1-wire bus
619#
620# CONFIG_W1 is not set
621
622#
623# Hardware Monitoring support
624#
625CONFIG_HWMON=y
626# CONFIG_HWMON_VID is not set
627# CONFIG_SENSORS_F71805F is not set
628# CONFIG_HWMON_DEBUG_CHIP is not set
629
630#
631# Misc devices
632#
633
634#
635# LED devices
636#
637# CONFIG_NEW_LEDS is not set
638
639#
640# LED drivers
641#
642
643#
644# LED Triggers
645#
646
647#
648# Multimedia devices
649#
650# CONFIG_VIDEO_DEV is not set
651CONFIG_VIDEO_V4L2=y
652
653#
654# Digital Video Broadcasting Devices
655#
656# CONFIG_DVB is not set
657
658#
659# Graphics support
660#
661CONFIG_FB=y
662CONFIG_FB_CFB_FILLRECT=y
663CONFIG_FB_CFB_COPYAREA=y
664CONFIG_FB_CFB_IMAGEBLIT=y
665# CONFIG_FB_MACMODES is not set
666CONFIG_FB_FIRMWARE_EDID=y
667# CONFIG_FB_MODE_HELPERS is not set
668# CONFIG_FB_TILEBLITTING is not set
669# CONFIG_FB_S1D13XXX is not set
670CONFIG_FB_PXA=y
671# CONFIG_FB_PXA_PARAMETERS is not set
672# CONFIG_FB_VIRTUAL is not set
673
674#
675# Console display driver support
676#
677# CONFIG_VGA_CONSOLE is not set
678CONFIG_DUMMY_CONSOLE=y
679CONFIG_FRAMEBUFFER_CONSOLE=y
680# CONFIG_FRAMEBUFFER_CONSOLE_ROTATION is not set
681# CONFIG_FONTS is not set
682CONFIG_FONT_8x8=y
683CONFIG_FONT_8x16=y
684
685#
686# Logo configuration
687#
688CONFIG_LOGO=y
689CONFIG_LOGO_LINUX_MONO=y
690CONFIG_LOGO_LINUX_VGA16=y
691CONFIG_LOGO_LINUX_CLUT224=y
692# CONFIG_BACKLIGHT_LCD_SUPPORT is not set
693
694#
695# Sound
696#
697CONFIG_SOUND=y
698
699#
700# Advanced Linux Sound Architecture
701#
702CONFIG_SND=y
703CONFIG_SND_TIMER=y
704CONFIG_SND_PCM=y
705# CONFIG_SND_SEQUENCER is not set
706# CONFIG_SND_MIXER_OSS is not set
707# CONFIG_SND_PCM_OSS is not set
708# CONFIG_SND_DYNAMIC_MINORS is not set
709# CONFIG_SND_SUPPORT_OLD_API is not set
710CONFIG_SND_VERBOSE_PROCFS=y
711# CONFIG_SND_VERBOSE_PRINTK is not set
712# CONFIG_SND_DEBUG is not set
713
714#
715# Generic devices
716#
717CONFIG_SND_AC97_CODEC=y
718CONFIG_SND_AC97_BUS=y
719# CONFIG_SND_DUMMY is not set
720# CONFIG_SND_MTPAV is not set
721# CONFIG_SND_SERIAL_U16550 is not set
722# CONFIG_SND_MPU401 is not set
723
724#
725# ALSA ARM devices
726#
727CONFIG_SND_PXA2XX_PCM=y
728CONFIG_SND_PXA2XX_AC97=y
729
730#
731# Open Sound System
732#
733# CONFIG_SOUND_PRIME is not set
734
735#
736# USB support
737#
738CONFIG_USB_ARCH_HAS_HCD=y
739CONFIG_USB_ARCH_HAS_OHCI=y
740# CONFIG_USB_ARCH_HAS_EHCI is not set
741# CONFIG_USB is not set
742
743#
744# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support'
745#
746
747#
748# USB Gadget Support
749#
750# CONFIG_USB_GADGET is not set
751
752#
753# MMC/SD Card support
754#
755# CONFIG_MMC is not set
756
757#
758# Real Time Clock
759#
760CONFIG_RTC_LIB=y
761# CONFIG_RTC_CLASS is not set
762
763#
764# File systems
765#
766CONFIG_EXT2_FS=y
767# CONFIG_EXT2_FS_XATTR is not set
768# CONFIG_EXT2_FS_XIP is not set
769# CONFIG_EXT3_FS is not set
770# CONFIG_REISERFS_FS is not set
771# CONFIG_JFS_FS is not set
772# CONFIG_FS_POSIX_ACL is not set
773# CONFIG_XFS_FS is not set
774# CONFIG_OCFS2_FS is not set
775# CONFIG_MINIX_FS is not set
776# CONFIG_ROMFS_FS is not set
777CONFIG_INOTIFY=y
778CONFIG_INOTIFY_USER=y
779# CONFIG_QUOTA is not set
780CONFIG_DNOTIFY=y
781# CONFIG_AUTOFS_FS is not set
782# CONFIG_AUTOFS4_FS is not set
783# CONFIG_FUSE_FS is not set
784
785#
786# CD-ROM/DVD Filesystems
787#
788# CONFIG_ISO9660_FS is not set
789# CONFIG_UDF_FS is not set
790
791#
792# DOS/FAT/NT Filesystems
793#
794CONFIG_FAT_FS=y
795CONFIG_MSDOS_FS=y
796# CONFIG_VFAT_FS is not set
797CONFIG_FAT_DEFAULT_CODEPAGE=437
798# CONFIG_NTFS_FS is not set
799
800#
801# Pseudo filesystems
802#
803CONFIG_PROC_FS=y
804CONFIG_SYSFS=y
805# CONFIG_TMPFS is not set
806# CONFIG_HUGETLB_PAGE is not set
807CONFIG_RAMFS=y
808# CONFIG_CONFIGFS_FS is not set
809
810#
811# Miscellaneous filesystems
812#
813# CONFIG_ADFS_FS is not set
814# CONFIG_AFFS_FS is not set
815# CONFIG_HFS_FS is not set
816# CONFIG_HFSPLUS_FS is not set
817# CONFIG_BEFS_FS is not set
818# CONFIG_BFS_FS is not set
819# CONFIG_EFS_FS is not set
820# CONFIG_JFFS_FS is not set
821CONFIG_JFFS2_FS=y
822CONFIG_JFFS2_FS_DEBUG=0
823CONFIG_JFFS2_FS_WRITEBUFFER=y
824# CONFIG_JFFS2_SUMMARY is not set
825# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
826CONFIG_JFFS2_ZLIB=y
827CONFIG_JFFS2_RTIME=y
828# CONFIG_JFFS2_RUBIN is not set
829# CONFIG_CRAMFS is not set
830# CONFIG_VXFS_FS is not set
831# CONFIG_HPFS_FS is not set
832# CONFIG_QNX4FS_FS is not set
833# CONFIG_SYSV_FS is not set
834# CONFIG_UFS_FS is not set
835
836#
837# Network File Systems
838#
839CONFIG_NFS_FS=y
840# CONFIG_NFS_V3 is not set
841# CONFIG_NFS_V4 is not set
842# CONFIG_NFS_DIRECTIO is not set
843# CONFIG_NFSD is not set
844CONFIG_ROOT_NFS=y
845CONFIG_LOCKD=y
846CONFIG_NFS_COMMON=y
847CONFIG_SUNRPC=y
848# CONFIG_RPCSEC_GSS_KRB5 is not set
849# CONFIG_RPCSEC_GSS_SPKM3 is not set
850# CONFIG_SMB_FS is not set
851# CONFIG_CIFS is not set
852# CONFIG_NCP_FS is not set
853# CONFIG_CODA_FS is not set
854# CONFIG_AFS_FS is not set
855# CONFIG_9P_FS is not set
856
857#
858# Partition Types
859#
860# CONFIG_PARTITION_ADVANCED is not set
861CONFIG_MSDOS_PARTITION=y
862
863#
864# Native Language Support
865#
866CONFIG_NLS=y
867CONFIG_NLS_DEFAULT="iso8859-1"
868# CONFIG_NLS_CODEPAGE_437 is not set
869# CONFIG_NLS_CODEPAGE_737 is not set
870# CONFIG_NLS_CODEPAGE_775 is not set
871# CONFIG_NLS_CODEPAGE_850 is not set
872# CONFIG_NLS_CODEPAGE_852 is not set
873# CONFIG_NLS_CODEPAGE_855 is not set
874# CONFIG_NLS_CODEPAGE_857 is not set
875# CONFIG_NLS_CODEPAGE_860 is not set
876# CONFIG_NLS_CODEPAGE_861 is not set
877# CONFIG_NLS_CODEPAGE_862 is not set
878# CONFIG_NLS_CODEPAGE_863 is not set
879# CONFIG_NLS_CODEPAGE_864 is not set
880# CONFIG_NLS_CODEPAGE_865 is not set
881# CONFIG_NLS_CODEPAGE_866 is not set
882# CONFIG_NLS_CODEPAGE_869 is not set
883# CONFIG_NLS_CODEPAGE_936 is not set
884# CONFIG_NLS_CODEPAGE_950 is not set
885# CONFIG_NLS_CODEPAGE_932 is not set
886# CONFIG_NLS_CODEPAGE_949 is not set
887# CONFIG_NLS_CODEPAGE_874 is not set
888# CONFIG_NLS_ISO8859_8 is not set
889# CONFIG_NLS_CODEPAGE_1250 is not set
890# CONFIG_NLS_CODEPAGE_1251 is not set
891# CONFIG_NLS_ASCII is not set
892CONFIG_NLS_ISO8859_1=y
893# CONFIG_NLS_ISO8859_2 is not set
894# CONFIG_NLS_ISO8859_3 is not set
895# CONFIG_NLS_ISO8859_4 is not set
896# CONFIG_NLS_ISO8859_5 is not set
897# CONFIG_NLS_ISO8859_6 is not set
898# CONFIG_NLS_ISO8859_7 is not set
899# CONFIG_NLS_ISO8859_9 is not set
900# CONFIG_NLS_ISO8859_13 is not set
901# CONFIG_NLS_ISO8859_14 is not set
902# CONFIG_NLS_ISO8859_15 is not set
903# CONFIG_NLS_KOI8_R is not set
904# CONFIG_NLS_KOI8_U is not set
905# CONFIG_NLS_UTF8 is not set
906
907#
908# Profiling support
909#
910# CONFIG_PROFILING is not set
911
912#
913# Kernel hacking
914#
915# CONFIG_PRINTK_TIME is not set
916CONFIG_MAGIC_SYSRQ=y
917CONFIG_DEBUG_KERNEL=y
918CONFIG_LOG_BUF_SHIFT=14
919CONFIG_DETECT_SOFTLOCKUP=y
920# CONFIG_SCHEDSTATS is not set
921# CONFIG_DEBUG_SLAB is not set
922# CONFIG_DEBUG_MUTEXES is not set
923# CONFIG_DEBUG_SPINLOCK is not set
924# CONFIG_DEBUG_SPINLOCK_SLEEP is not set
925# CONFIG_DEBUG_KOBJECT is not set
926CONFIG_DEBUG_BUGVERBOSE=y
927CONFIG_DEBUG_INFO=y
928# CONFIG_DEBUG_FS is not set
929# CONFIG_DEBUG_VM is not set
930CONFIG_FRAME_POINTER=y
931# CONFIG_UNWIND_INFO is not set
932CONFIG_FORCED_INLINING=y
933# CONFIG_RCU_TORTURE_TEST is not set
934CONFIG_DEBUG_USER=y
935# CONFIG_DEBUG_WAITQ is not set
936CONFIG_DEBUG_ERRORS=y
937CONFIG_DEBUG_LL=y
938# CONFIG_DEBUG_ICEDCC is not set
939
940#
941# Security options
942#
943# CONFIG_KEYS is not set
944# CONFIG_SECURITY is not set
945
946#
947# Cryptographic options
948#
949# CONFIG_CRYPTO is not set
950
951#
952# Hardware crypto devices
953#
954
955#
956# Library routines
957#
958# CONFIG_CRC_CCITT is not set
959# CONFIG_CRC16 is not set
960CONFIG_CRC32=y
961# CONFIG_LIBCRC32C is not set
962CONFIG_ZLIB_INFLATE=y
963CONFIG_ZLIB_DEFLATE=y
diff --git a/arch/arm/kernel/entry-armv.S b/arch/arm/kernel/entry-armv.S
index ab8e600c18c8..86c92523a346 100644
--- a/arch/arm/kernel/entry-armv.S
+++ b/arch/arm/kernel/entry-armv.S
@@ -20,6 +20,7 @@
20#include <asm/glue.h> 20#include <asm/glue.h>
21#include <asm/vfpmacros.h> 21#include <asm/vfpmacros.h>
22#include <asm/arch/entry-macro.S> 22#include <asm/arch/entry-macro.S>
23#include <asm/thread_notify.h>
23 24
24#include "entry-header.S" 25#include "entry-header.S"
25 26
@@ -560,10 +561,8 @@ ENTRY(__switch_to)
560 add ip, r1, #TI_CPU_SAVE 561 add ip, r1, #TI_CPU_SAVE
561 ldr r3, [r2, #TI_TP_VALUE] 562 ldr r3, [r2, #TI_TP_VALUE]
562 stmia ip!, {r4 - sl, fp, sp, lr} @ Store most regs on stack 563 stmia ip!, {r4 - sl, fp, sp, lr} @ Store most regs on stack
563#ifndef CONFIG_MMU 564#ifdef CONFIG_MMU
564 add r2, r2, #TI_CPU_DOMAIN 565 ldr r6, [r2, #TI_CPU_DOMAIN]
565#else
566 ldr r6, [r2, #TI_CPU_DOMAIN]!
567#endif 566#endif
568#if __LINUX_ARM_ARCH__ >= 6 567#if __LINUX_ARM_ARCH__ >= 6
569#ifdef CONFIG_CPU_32v6K 568#ifdef CONFIG_CPU_32v6K
@@ -585,21 +584,20 @@ ENTRY(__switch_to)
585#ifdef CONFIG_MMU 584#ifdef CONFIG_MMU
586 mcr p15, 0, r6, c3, c0, 0 @ Set domain register 585 mcr p15, 0, r6, c3, c0, 0 @ Set domain register
587#endif 586#endif
588#ifdef CONFIG_VFP
589 @ Always disable VFP so we can lazily save/restore the old
590 @ state. This occurs in the context of the previous thread.
591 VFPFMRX r4, FPEXC
592 bic r4, r4, #FPEXC_ENABLE
593 VFPFMXR FPEXC, r4
594#endif
595#if defined(CONFIG_IWMMXT) 587#if defined(CONFIG_IWMMXT)
596 bl iwmmxt_task_switch 588 bl iwmmxt_task_switch
597#elif defined(CONFIG_CPU_XSCALE) 589#elif defined(CONFIG_CPU_XSCALE)
598 add r4, r2, #40 @ cpu_context_save->extra 590 add r4, r2, #TI_CPU_DOMAIN + 40 @ cpu_context_save->extra
599 ldmib r4, {r4, r5} 591 ldmib r4, {r4, r5}
600 mar acc0, r4, r5 592 mar acc0, r4, r5
601#endif 593#endif
602 ldmib r2, {r4 - sl, fp, sp, pc} @ Load all regs saved previously 594 mov r5, r0
595 add r4, r2, #TI_CPU_SAVE
596 ldr r0, =thread_notify_head
597 mov r1, #THREAD_NOTIFY_SWITCH
598 bl atomic_notifier_call_chain
599 mov r0, r5
600 ldmia r4, {r4 - sl, fp, sp, pc} @ Load all regs saved previously
603 601
604 __INIT 602 __INIT
605 603
diff --git a/arch/arm/kernel/iwmmxt.S b/arch/arm/kernel/iwmmxt.S
index 24c7b0477a09..af9e0ae952d5 100644
--- a/arch/arm/kernel/iwmmxt.S
+++ b/arch/arm/kernel/iwmmxt.S
@@ -285,7 +285,7 @@ ENTRY(iwmmxt_task_switch)
285 bne 1f @ yes: block them for next task 285 bne 1f @ yes: block them for next task
286 286
287 ldr r5, =concan_owner 287 ldr r5, =concan_owner
288 add r6, r2, #(TI_IWMMXT_STATE - TI_CPU_DOMAIN) @ get next task Concan save area 288 add r6, r2, #TI_IWMMXT_STATE @ get next task Concan save area
289 ldr r5, [r5] @ get current Concan owner 289 ldr r5, [r5] @ get current Concan owner
290 teq r5, r6 @ next task owns it? 290 teq r5, r6 @ next task owns it?
291 movne pc, lr @ no: leave Concan disabled 291 movne pc, lr @ no: leave Concan disabled
diff --git a/arch/arm/kernel/process.c b/arch/arm/kernel/process.c
index 17c38dbf2f3c..e1c77ee885a7 100644
--- a/arch/arm/kernel/process.c
+++ b/arch/arm/kernel/process.c
@@ -33,6 +33,7 @@
33#include <asm/leds.h> 33#include <asm/leds.h>
34#include <asm/processor.h> 34#include <asm/processor.h>
35#include <asm/system.h> 35#include <asm/system.h>
36#include <asm/thread_notify.h>
36#include <asm/uaccess.h> 37#include <asm/uaccess.h>
37#include <asm/mach/time.h> 38#include <asm/mach/time.h>
38 39
@@ -338,13 +339,9 @@ void exit_thread(void)
338{ 339{
339} 340}
340 341
341static void default_fp_init(union fp_state *fp) 342ATOMIC_NOTIFIER_HEAD(thread_notify_head);
342{
343 memset(fp, 0, sizeof(union fp_state));
344}
345 343
346void (*fp_init)(union fp_state *) = default_fp_init; 344EXPORT_SYMBOL_GPL(thread_notify_head);
347EXPORT_SYMBOL(fp_init);
348 345
349void flush_thread(void) 346void flush_thread(void)
350{ 347{
@@ -353,22 +350,21 @@ void flush_thread(void)
353 350
354 memset(thread->used_cp, 0, sizeof(thread->used_cp)); 351 memset(thread->used_cp, 0, sizeof(thread->used_cp));
355 memset(&tsk->thread.debug, 0, sizeof(struct debug_info)); 352 memset(&tsk->thread.debug, 0, sizeof(struct debug_info));
353 memset(&thread->fpstate, 0, sizeof(union fp_state));
354
355 thread_notify(THREAD_NOTIFY_FLUSH, thread);
356#if defined(CONFIG_IWMMXT) 356#if defined(CONFIG_IWMMXT)
357 iwmmxt_task_release(thread); 357 iwmmxt_task_release(thread);
358#endif 358#endif
359 fp_init(&thread->fpstate);
360#if defined(CONFIG_VFP)
361 vfp_flush_thread(&thread->vfpstate);
362#endif
363} 359}
364 360
365void release_thread(struct task_struct *dead_task) 361void release_thread(struct task_struct *dead_task)
366{ 362{
367#if defined(CONFIG_VFP) 363 struct thread_info *thread = task_thread_info(dead_task);
368 vfp_release_thread(&task_thread_info(dead_task)->vfpstate); 364
369#endif 365 thread_notify(THREAD_NOTIFY_RELEASE, thread);
370#if defined(CONFIG_IWMMXT) 366#if defined(CONFIG_IWMMXT)
371 iwmmxt_task_release(task_thread_info(dead_task)); 367 iwmmxt_task_release(thread);
372#endif 368#endif
373} 369}
374 370
diff --git a/arch/arm/kernel/signal.c b/arch/arm/kernel/signal.c
index a0cd0a90a10d..e9fe78033361 100644
--- a/arch/arm/kernel/signal.c
+++ b/arch/arm/kernel/signal.c
@@ -665,17 +665,33 @@ static int do_signal(sigset_t *oldset, struct pt_regs *regs, int syscall)
665 if (syscall) { 665 if (syscall) {
666 if (regs->ARM_r0 == -ERESTART_RESTARTBLOCK) { 666 if (regs->ARM_r0 == -ERESTART_RESTARTBLOCK) {
667 if (thumb_mode(regs)) { 667 if (thumb_mode(regs)) {
668 regs->ARM_r7 = __NR_restart_syscall; 668 regs->ARM_r7 = __NR_restart_syscall - __NR_SYSCALL_BASE;
669 regs->ARM_pc -= 2; 669 regs->ARM_pc -= 2;
670 } else { 670 } else {
671#if defined(CONFIG_AEABI) && !defined(CONFIG_OABI_COMPAT)
672 regs->ARM_r7 = __NR_restart_syscall;
673 regs->ARM_pc -= 4;
674#else
671 u32 __user *usp; 675 u32 __user *usp;
676 u32 swival = __NR_restart_syscall;
672 677
673 regs->ARM_sp -= 12; 678 regs->ARM_sp -= 12;
674 usp = (u32 __user *)regs->ARM_sp; 679 usp = (u32 __user *)regs->ARM_sp;
675 680
681 /*
682 * Either we supports OABI only, or we have
683 * EABI with the OABI compat layer enabled.
684 * In the later case we don't know if user
685 * space is EABI or not, and if not we must
686 * not clobber r7. Always using the OABI
687 * syscall solves that issue and works for
688 * all those cases.
689 */
690 swival = swival - __NR_SYSCAll_BASE + __NR_OABI_SYSCALL_BASE;
691
676 put_user(regs->ARM_pc, &usp[0]); 692 put_user(regs->ARM_pc, &usp[0]);
677 /* swi __NR_restart_syscall */ 693 /* swi __NR_restart_syscall */
678 put_user(0xef000000 | __NR_restart_syscall, &usp[1]); 694 put_user(0xef000000 | swival, &usp[1]);
679 /* ldr pc, [sp], #12 */ 695 /* ldr pc, [sp], #12 */
680 put_user(0xe49df00c, &usp[2]); 696 put_user(0xe49df00c, &usp[2]);
681 697
@@ -683,6 +699,7 @@ static int do_signal(sigset_t *oldset, struct pt_regs *regs, int syscall)
683 (unsigned long)(usp + 3)); 699 (unsigned long)(usp + 3));
684 700
685 regs->ARM_pc = regs->ARM_sp + 4; 701 regs->ARM_pc = regs->ARM_sp + 4;
702#endif
686 } 703 }
687 } 704 }
688 if (regs->ARM_r0 == -ERESTARTNOHAND || 705 if (regs->ARM_r0 == -ERESTARTNOHAND ||
diff --git a/arch/arm/mach-ep93xx/core.c b/arch/arm/mach-ep93xx/core.c
index dcd417625389..bf6bd71bdd08 100644
--- a/arch/arm/mach-ep93xx/core.c
+++ b/arch/arm/mach-ep93xx/core.c
@@ -103,7 +103,8 @@ static int ep93xx_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
103 write_seqlock(&xtime_lock); 103 write_seqlock(&xtime_lock);
104 104
105 __raw_writel(1, EP93XX_TIMER1_CLEAR); 105 __raw_writel(1, EP93XX_TIMER1_CLEAR);
106 while (__raw_readl(EP93XX_TIMER4_VALUE_LOW) - last_jiffy_time 106 while ((signed long)
107 (__raw_readl(EP93XX_TIMER4_VALUE_LOW) - last_jiffy_time)
107 >= TIMER4_TICKS_PER_JIFFY) { 108 >= TIMER4_TICKS_PER_JIFFY) {
108 last_jiffy_time += TIMER4_TICKS_PER_JIFFY; 109 last_jiffy_time += TIMER4_TICKS_PER_JIFFY;
109 timer_tick(regs); 110 timer_tick(regs);
@@ -124,7 +125,7 @@ static void __init ep93xx_timer_init(void)
124{ 125{
125 /* Enable periodic HZ timer. */ 126 /* Enable periodic HZ timer. */
126 __raw_writel(0x48, EP93XX_TIMER1_CONTROL); 127 __raw_writel(0x48, EP93XX_TIMER1_CONTROL);
127 __raw_writel((508000 / HZ) - 1, EP93XX_TIMER1_LOAD); 128 __raw_writel((508469 / HZ) - 1, EP93XX_TIMER1_LOAD);
128 __raw_writel(0xc8, EP93XX_TIMER1_CONTROL); 129 __raw_writel(0xc8, EP93XX_TIMER1_CONTROL);
129 130
130 /* Enable lost jiffy timer. */ 131 /* Enable lost jiffy timer. */
diff --git a/arch/arm/mach-ep93xx/gesbc9312.c b/arch/arm/mach-ep93xx/gesbc9312.c
index d18fcb1a2f1b..47cc6c8b7c79 100644
--- a/arch/arm/mach-ep93xx/gesbc9312.c
+++ b/arch/arm/mach-ep93xx/gesbc9312.c
@@ -16,16 +16,38 @@
16#include <linux/mm.h> 16#include <linux/mm.h>
17#include <linux/sched.h> 17#include <linux/sched.h>
18#include <linux/interrupt.h> 18#include <linux/interrupt.h>
19#include <linux/ioport.h>
19#include <linux/mtd/physmap.h> 20#include <linux/mtd/physmap.h>
21#include <linux/platform_device.h>
20#include <asm/io.h> 22#include <asm/io.h>
21#include <asm/hardware.h> 23#include <asm/hardware.h>
22#include <asm/mach-types.h> 24#include <asm/mach-types.h>
23#include <asm/mach/arch.h> 25#include <asm/mach/arch.h>
24 26
27static struct physmap_flash_data gesbc9312_flash_data = {
28 .width = 4,
29};
30
31static struct resource gesbc9312_flash_resource = {
32 .start = 0x60000000,
33 .end = 0x60800000,
34 .flags = IORESOURCE_MEM,
35};
36
37static struct platform_device gesbc9312_flash = {
38 .name = "physmap-flash",
39 .id = 0,
40 .dev = {
41 .platform_data = &gesbc9312_flash_data,
42 },
43 .num_resources = 1,
44 .resource = &gesbc9312_flash_resource,
45};
46
25static void __init gesbc9312_init_machine(void) 47static void __init gesbc9312_init_machine(void)
26{ 48{
27 ep93xx_init_devices(); 49 ep93xx_init_devices();
28 physmap_configure(0x60000000, 0x00800000, 4, NULL); 50 platform_device_register(&gesbc9312_flash);
29} 51}
30 52
31MACHINE_START(GESBC9312, "Glomation GESBC-9312-sx") 53MACHINE_START(GESBC9312, "Glomation GESBC-9312-sx")
diff --git a/arch/arm/mach-ep93xx/ts72xx.c b/arch/arm/mach-ep93xx/ts72xx.c
index e24566b88a78..6e5a56cd5ae8 100644
--- a/arch/arm/mach-ep93xx/ts72xx.c
+++ b/arch/arm/mach-ep93xx/ts72xx.c
@@ -16,6 +16,7 @@
16#include <linux/mm.h> 16#include <linux/mm.h>
17#include <linux/sched.h> 17#include <linux/sched.h>
18#include <linux/interrupt.h> 18#include <linux/interrupt.h>
19#include <linux/ioport.h>
19#include <linux/mtd/physmap.h> 20#include <linux/mtd/physmap.h>
20#include <linux/platform_device.h> 21#include <linux/platform_device.h>
21#include <linux/m48t86.h> 22#include <linux/m48t86.h>
@@ -111,6 +112,26 @@ static void __init ts72xx_map_io(void)
111 } 112 }
112} 113}
113 114
115static struct physmap_flash_data ts72xx_flash_data = {
116 .width = 1,
117};
118
119static struct resource ts72xx_flash_resource = {
120 .start = TS72XX_NOR_PHYS_BASE,
121 .end = TS72XX_NOR_PHYS_BASE + 0x01000000,
122 .flags = IORESOURCE_MEM,
123};
124
125static struct platform_device ts72xx_flash = {
126 .name = "physmap-flash",
127 .id = 0,
128 .dev = {
129 .platform_data = &ts72xx_flash_data,
130 },
131 .num_resources = 1,
132 .resource = &ts72xx_flash_resource,
133};
134
114static unsigned char ts72xx_rtc_readbyte(unsigned long addr) 135static unsigned char ts72xx_rtc_readbyte(unsigned long addr)
115{ 136{
116 __raw_writeb(addr, TS72XX_RTC_INDEX_VIRT_BASE); 137 __raw_writeb(addr, TS72XX_RTC_INDEX_VIRT_BASE);
@@ -141,7 +162,7 @@ static void __init ts72xx_init_machine(void)
141{ 162{
142 ep93xx_init_devices(); 163 ep93xx_init_devices();
143 if (board_is_ts7200()) 164 if (board_is_ts7200())
144 physmap_configure(TS72XX_NOR_PHYS_BASE, 0x01000000, 1, NULL); 165 platform_device_register(&ts72xx_flash);
145 platform_device_register(&ts72xx_rtc_device); 166 platform_device_register(&ts72xx_rtc_device);
146} 167}
147 168
diff --git a/arch/arm/mach-imx/dma.c b/arch/arm/mach-imx/dma.c
index 4ca51dcf13ac..36578871ecc8 100644
--- a/arch/arm/mach-imx/dma.c
+++ b/arch/arm/mach-imx/dma.c
@@ -15,6 +15,9 @@
15 * Changed to support scatter gather DMA 15 * Changed to support scatter gather DMA
16 * by taking Russell's code from RiscPC 16 * by taking Russell's code from RiscPC
17 * 17 *
18 * 2006-05-31 Pavel Pisa <pisa@cmp.felk.cvut.cz>
19 * Corrected error handling code.
20 *
18 */ 21 */
19 22
20#undef DEBUG 23#undef DEBUG
@@ -277,7 +280,7 @@ imx_dma_setup_sg(imx_dmach_t dma_ch,
277int 280int
278imx_dma_setup_handlers(imx_dmach_t dma_ch, 281imx_dma_setup_handlers(imx_dmach_t dma_ch,
279 void (*irq_handler) (int, void *, struct pt_regs *), 282 void (*irq_handler) (int, void *, struct pt_regs *),
280 void (*err_handler) (int, void *, struct pt_regs *), 283 void (*err_handler) (int, void *, struct pt_regs *, int),
281 void *data) 284 void *data)
282{ 285{
283 struct imx_dma_channel *imxdma = &imx_dma_channels[dma_ch]; 286 struct imx_dma_channel *imxdma = &imx_dma_channels[dma_ch];
@@ -463,43 +466,53 @@ static irqreturn_t dma_err_handler(int irq, void *dev_id, struct pt_regs *regs)
463 int i, disr = DISR; 466 int i, disr = DISR;
464 struct imx_dma_channel *channel; 467 struct imx_dma_channel *channel;
465 unsigned int err_mask = DBTOSR | DRTOSR | DSESR | DBOSR; 468 unsigned int err_mask = DBTOSR | DRTOSR | DSESR | DBOSR;
469 int errcode;
466 470
467 DISR = disr; 471 DISR = disr & err_mask;
468 for (i = 0; i < IMX_DMA_CHANNELS; i++) { 472 for (i = 0; i < IMX_DMA_CHANNELS; i++) {
469 channel = &imx_dma_channels[i]; 473 if(!(err_mask & (1 << i)))
470
471 if ((err_mask & 1 << i) && channel->name
472 && channel->err_handler) {
473 channel->err_handler(i, channel->data, regs);
474 continue; 474 continue;
475 } 475 channel = &imx_dma_channels[i];
476 476 errcode = 0;
477 imx_dma_channels[i].sg = NULL;
478 477
479 if (DBTOSR & (1 << i)) { 478 if (DBTOSR & (1 << i)) {
480 printk(KERN_WARNING 479 DBTOSR = (1 << i);
481 "Burst timeout on channel %d (%s)\n", 480 errcode |= IMX_DMA_ERR_BURST;
482 i, channel->name);
483 DBTOSR |= (1 << i);
484 } 481 }
485 if (DRTOSR & (1 << i)) { 482 if (DRTOSR & (1 << i)) {
486 printk(KERN_WARNING 483 DRTOSR = (1 << i);
487 "Request timeout on channel %d (%s)\n", 484 errcode |= IMX_DMA_ERR_REQUEST;
488 i, channel->name);
489 DRTOSR |= (1 << i);
490 } 485 }
491 if (DSESR & (1 << i)) { 486 if (DSESR & (1 << i)) {
492 printk(KERN_WARNING 487 DSESR = (1 << i);
493 "Transfer timeout on channel %d (%s)\n", 488 errcode |= IMX_DMA_ERR_TRANSFER;
494 i, channel->name);
495 DSESR |= (1 << i);
496 } 489 }
497 if (DBOSR & (1 << i)) { 490 if (DBOSR & (1 << i)) {
498 printk(KERN_WARNING 491 DBOSR = (1 << i);
499 "Buffer overflow timeout on channel %d (%s)\n", 492 errcode |= IMX_DMA_ERR_BUFFER;
500 i, channel->name);
501 DBOSR |= (1 << i);
502 } 493 }
494
495 /*
496 * The cleaning of @sg field would be questionable
497 * there, because its value can help to compute
498 * remaining/transfered bytes count in the handler
499 */
500 /*imx_dma_channels[i].sg = NULL;*/
501
502 if (channel->name && channel->err_handler) {
503 channel->err_handler(i, channel->data, regs, errcode);
504 continue;
505 }
506
507 imx_dma_channels[i].sg = NULL;
508
509 printk(KERN_WARNING
510 "DMA timeout on channel %d (%s) -%s%s%s%s\n",
511 i, channel->name,
512 errcode&IMX_DMA_ERR_BURST? " burst":"",
513 errcode&IMX_DMA_ERR_REQUEST? " request":"",
514 errcode&IMX_DMA_ERR_TRANSFER? " transfer":"",
515 errcode&IMX_DMA_ERR_BUFFER? " buffer":"");
503 } 516 }
504 return IRQ_HANDLED; 517 return IRQ_HANDLED;
505} 518}
diff --git a/arch/arm/mach-ixp2000/core.c b/arch/arm/mach-ixp2000/core.c
index 6e8d504aca55..186f632035b8 100644
--- a/arch/arm/mach-ixp2000/core.c
+++ b/arch/arm/mach-ixp2000/core.c
@@ -211,7 +211,8 @@ static int ixp2000_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
211 /* clear timer 1 */ 211 /* clear timer 1 */
212 ixp2000_reg_wrb(IXP2000_T1_CLR, 1); 212 ixp2000_reg_wrb(IXP2000_T1_CLR, 1);
213 213
214 while ((next_jiffy_time - *missing_jiffy_timer_csr) > ticks_per_jiffy) { 214 while ((signed long)(next_jiffy_time - *missing_jiffy_timer_csr)
215 >= ticks_per_jiffy) {
215 timer_tick(regs); 216 timer_tick(regs);
216 next_jiffy_time -= ticks_per_jiffy; 217 next_jiffy_time -= ticks_per_jiffy;
217 } 218 }
diff --git a/arch/arm/mach-ixp23xx/core.c b/arch/arm/mach-ixp23xx/core.c
index affd1d5d7440..051e3d70026e 100644
--- a/arch/arm/mach-ixp23xx/core.c
+++ b/arch/arm/mach-ixp23xx/core.c
@@ -334,7 +334,7 @@ void __init ixp23xx_init_irq(void)
334/************************************************************************* 334/*************************************************************************
335 * Timer-tick functions for IXP23xx 335 * Timer-tick functions for IXP23xx
336 *************************************************************************/ 336 *************************************************************************/
337#define CLOCK_TICKS_PER_USEC CLOCK_TICK_RATE / (USEC_PER_SEC) 337#define CLOCK_TICKS_PER_USEC (CLOCK_TICK_RATE / USEC_PER_SEC)
338 338
339static unsigned long next_jiffy_time; 339static unsigned long next_jiffy_time;
340 340
@@ -353,7 +353,7 @@ ixp23xx_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs)
353{ 353{
354 /* Clear Pending Interrupt by writing '1' to it */ 354 /* Clear Pending Interrupt by writing '1' to it */
355 *IXP23XX_TIMER_STATUS = IXP23XX_TIMER1_INT_PEND; 355 *IXP23XX_TIMER_STATUS = IXP23XX_TIMER1_INT_PEND;
356 while ((*IXP23XX_TIMER_CONT - next_jiffy_time) > LATCH) { 356 while ((signed long)(*IXP23XX_TIMER_CONT - next_jiffy_time) >= LATCH) {
357 timer_tick(regs); 357 timer_tick(regs);
358 next_jiffy_time += LATCH; 358 next_jiffy_time += LATCH;
359 } 359 }
@@ -439,5 +439,6 @@ static struct platform_device *ixp23xx_devices[] __initdata = {
439 439
440void __init ixp23xx_sys_init(void) 440void __init ixp23xx_sys_init(void)
441{ 441{
442 *IXP23XX_EXP_UNIT_FUSE |= 0xf;
442 platform_add_devices(ixp23xx_devices, ARRAY_SIZE(ixp23xx_devices)); 443 platform_add_devices(ixp23xx_devices, ARRAY_SIZE(ixp23xx_devices));
443} 444}
diff --git a/arch/arm/mach-ixp23xx/espresso.c b/arch/arm/mach-ixp23xx/espresso.c
index bf688c128630..dc5e489c70bc 100644
--- a/arch/arm/mach-ixp23xx/espresso.c
+++ b/arch/arm/mach-ixp23xx/espresso.c
@@ -53,9 +53,29 @@ static int __init espresso_pci_init(void)
53}; 53};
54subsys_initcall(espresso_pci_init); 54subsys_initcall(espresso_pci_init);
55 55
56static struct physmap_flash_data espresso_flash_data = {
57 .width = 2,
58};
59
60static struct resource espresso_flash_resource = {
61 .start = 0x90000000,
62 .end = 0x92000000,
63 .flags = IORESOURCE_MEM,
64};
65
66static struct platform_device espresso_flash = {
67 .name = "physmap-flash",
68 .id = 0,
69 .dev = {
70 .platform_data = &espresso_flash_data,
71 },
72 .num_resources = 1,
73 .resource = &espresso_flash_resource,
74};
75
56static void __init espresso_init(void) 76static void __init espresso_init(void)
57{ 77{
58 physmap_configure(0x90000000, 0x02000000, 2, NULL); 78 platform_device_register(&espresso_flash);
59 79
60 /* 80 /*
61 * Mark flash as writeable. 81 * Mark flash as writeable.
diff --git a/arch/arm/mach-ixp23xx/ixdp2351.c b/arch/arm/mach-ixp23xx/ixdp2351.c
index 00146c35daac..535b334ee045 100644
--- a/arch/arm/mach-ixp23xx/ixdp2351.c
+++ b/arch/arm/mach-ixp23xx/ixdp2351.c
@@ -298,9 +298,29 @@ static void __init ixdp2351_map_io(void)
298 iotable_init(ixdp2351_io_desc, ARRAY_SIZE(ixdp2351_io_desc)); 298 iotable_init(ixdp2351_io_desc, ARRAY_SIZE(ixdp2351_io_desc));
299} 299}
300 300
301static struct physmap_flash_data ixdp2351_flash_data = {
302 .width = 1,
303};
304
305static struct resource ixdp2351_flash_resource = {
306 .start = 0x90000000,
307 .end = 0x94000000,
308 .flags = IORESOURCE_MEM,
309};
310
311static struct platform_device ixdp2351_flash = {
312 .name = "physmap-flash",
313 .id = 0,
314 .dev = {
315 .platform_data = &ixdp2351_flash_data,
316 },
317 .num_resources = 1,
318 .resource = &ixdp2351_flash_resource,
319};
320
301static void __init ixdp2351_init(void) 321static void __init ixdp2351_init(void)
302{ 322{
303 physmap_configure(0x90000000, 0x04000000, 1, NULL); 323 platform_device_register(&ixdp2351_flash);
304 324
305 /* 325 /*
306 * Mark flash as writeable 326 * Mark flash as writeable
diff --git a/arch/arm/mach-ixp23xx/roadrunner.c b/arch/arm/mach-ixp23xx/roadrunner.c
index 43c14e740794..b9f5d13fcfe1 100644
--- a/arch/arm/mach-ixp23xx/roadrunner.c
+++ b/arch/arm/mach-ixp23xx/roadrunner.c
@@ -137,9 +137,29 @@ static int __init roadrunner_pci_init(void)
137 137
138subsys_initcall(roadrunner_pci_init); 138subsys_initcall(roadrunner_pci_init);
139 139
140static struct physmap_flash_data roadrunner_flash_data = {
141 .width = 2,
142};
143
144static struct resource roadrunner_flash_resource = {
145 .start = 0x90000000,
146 .end = 0x94000000,
147 .flags = IORESOURCE_MEM,
148};
149
150static struct platform_device roadrunner_flash = {
151 .name = "physmap-flash",
152 .id = 0,
153 .dev = {
154 .platform_data = &roadrunner_flash_data,
155 },
156 .num_resources = 1,
157 .resource = &roadrunner_flash_resource,
158};
159
140static void __init roadrunner_init(void) 160static void __init roadrunner_init(void)
141{ 161{
142 physmap_configure(0x90000000, 0x04000000, 2, NULL); 162 platform_device_register(&roadrunner_flash);
143 163
144 /* 164 /*
145 * Mark flash as writeable 165 * Mark flash as writeable
diff --git a/arch/arm/mach-ixp4xx/common.c b/arch/arm/mach-ixp4xx/common.c
index 00b761ff0f9c..bf25a76e9bdf 100644
--- a/arch/arm/mach-ixp4xx/common.c
+++ b/arch/arm/mach-ixp4xx/common.c
@@ -276,7 +276,7 @@ static irqreturn_t ixp4xx_timer_interrupt(int irq, void *dev_id, struct pt_regs
276 /* 276 /*
277 * Catch up with the real idea of time 277 * Catch up with the real idea of time
278 */ 278 */
279 while ((*IXP4XX_OSTS - last_jiffy_time) > LATCH) { 279 while ((signed long)(*IXP4XX_OSTS - last_jiffy_time) >= LATCH) {
280 timer_tick(regs); 280 timer_tick(regs);
281 last_jiffy_time += LATCH; 281 last_jiffy_time += LATCH;
282 } 282 }
diff --git a/arch/arm/mach-ixp4xx/nas100d-setup.c b/arch/arm/mach-ixp4xx/nas100d-setup.c
index a3b4c6ac5708..9a31444d9214 100644
--- a/arch/arm/mach-ixp4xx/nas100d-setup.c
+++ b/arch/arm/mach-ixp4xx/nas100d-setup.c
@@ -15,6 +15,7 @@
15#include <linux/kernel.h> 15#include <linux/kernel.h>
16#include <linux/serial.h> 16#include <linux/serial.h>
17#include <linux/serial_8250.h> 17#include <linux/serial_8250.h>
18#include <linux/leds.h>
18 19
19#include <asm/mach-types.h> 20#include <asm/mach-types.h>
20#include <asm/mach/arch.h> 21#include <asm/mach/arch.h>
@@ -37,6 +38,36 @@ static struct platform_device nas100d_flash = {
37 .resource = &nas100d_flash_resource, 38 .resource = &nas100d_flash_resource,
38}; 39};
39 40
41#ifdef CONFIG_LEDS_IXP4XX
42static struct resource nas100d_led_resources[] = {
43 {
44 .name = "wlan", /* green led */
45 .start = 0,
46 .end = 0,
47 .flags = IXP4XX_GPIO_LOW,
48 },
49 {
50 .name = "ready", /* blue power led (off is flashing!) */
51 .start = 15,
52 .end = 15,
53 .flags = IXP4XX_GPIO_LOW,
54 },
55 {
56 .name = "disk", /* yellow led */
57 .start = 3,
58 .end = 3,
59 .flags = IXP4XX_GPIO_LOW,
60 },
61};
62
63static struct platform_device nas100d_leds = {
64 .name = "IXP4XX-GPIO-LED",
65 .id = -1,
66 .num_resources = ARRAY_SIZE(nas100d_led_resources),
67 .resource = nas100d_led_resources,
68};
69#endif
70
40static struct ixp4xx_i2c_pins nas100d_i2c_gpio_pins = { 71static struct ixp4xx_i2c_pins nas100d_i2c_gpio_pins = {
41 .sda_pin = NAS100D_SDA_PIN, 72 .sda_pin = NAS100D_SDA_PIN,
42 .scl_pin = NAS100D_SCL_PIN, 73 .scl_pin = NAS100D_SCL_PIN,
@@ -95,7 +126,9 @@ static struct platform_device nas100d_uart = {
95static struct platform_device *nas100d_devices[] __initdata = { 126static struct platform_device *nas100d_devices[] __initdata = {
96 &nas100d_i2c_controller, 127 &nas100d_i2c_controller,
97 &nas100d_flash, 128 &nas100d_flash,
98 &nas100d_uart, 129#ifdef CONFIG_LEDS_IXP4XX
130 &nas100d_leds,
131#endif
99}; 132};
100 133
101static void nas100d_power_off(void) 134static void nas100d_power_off(void)
@@ -122,6 +155,12 @@ static void __init nas100d_init(void)
122 155
123 pm_power_off = nas100d_power_off; 156 pm_power_off = nas100d_power_off;
124 157
158 /* This is only useful on a modified machine, but it is valuable
159 * to have it first in order to see debug messages, and so that
160 * it does *not* get removed if platform_add_devices fails!
161 */
162 (void)platform_device_register(&nas100d_uart);
163
125 platform_add_devices(nas100d_devices, ARRAY_SIZE(nas100d_devices)); 164 platform_add_devices(nas100d_devices, ARRAY_SIZE(nas100d_devices));
126} 165}
127 166
diff --git a/arch/arm/mach-ixp4xx/nslu2-setup.c b/arch/arm/mach-ixp4xx/nslu2-setup.c
index 55411f21d838..749a337494d3 100644
--- a/arch/arm/mach-ixp4xx/nslu2-setup.c
+++ b/arch/arm/mach-ixp4xx/nslu2-setup.c
@@ -7,6 +7,7 @@
7 * Copyright (C) 2003-2004 MontaVista Software, Inc. 7 * Copyright (C) 2003-2004 MontaVista Software, Inc.
8 * 8 *
9 * Author: Mark Rakes <mrakes at mac.com> 9 * Author: Mark Rakes <mrakes at mac.com>
10 * Author: Rod Whitby <rod@whitby.id.au>
10 * Maintainers: http://www.nslu2-linux.org/ 11 * Maintainers: http://www.nslu2-linux.org/
11 * 12 *
12 * Fixed missing init_time in MACHINE_START kas11 10/22/04 13 * Fixed missing init_time in MACHINE_START kas11 10/22/04
@@ -16,6 +17,7 @@
16#include <linux/kernel.h> 17#include <linux/kernel.h>
17#include <linux/serial.h> 18#include <linux/serial.h>
18#include <linux/serial_8250.h> 19#include <linux/serial_8250.h>
20#include <linux/leds.h>
19 21
20#include <asm/mach-types.h> 22#include <asm/mach-types.h>
21#include <asm/mach/arch.h> 23#include <asm/mach/arch.h>
@@ -43,6 +45,42 @@ static struct ixp4xx_i2c_pins nslu2_i2c_gpio_pins = {
43 .scl_pin = NSLU2_SCL_PIN, 45 .scl_pin = NSLU2_SCL_PIN,
44}; 46};
45 47
48#ifdef CONFIG_LEDS_IXP4XX
49static struct resource nslu2_led_resources[] = {
50 {
51 .name = "ready", /* green led */
52 .start = NSLU2_LED_GRN,
53 .end = NSLU2_LED_GRN,
54 .flags = IXP4XX_GPIO_HIGH,
55 },
56 {
57 .name = "status", /* red led */
58 .start = NSLU2_LED_RED,
59 .end = NSLU2_LED_RED,
60 .flags = IXP4XX_GPIO_HIGH,
61 },
62 {
63 .name = "disk-1",
64 .start = NSLU2_LED_DISK1,
65 .end = NSLU2_LED_DISK1,
66 .flags = IXP4XX_GPIO_LOW,
67 },
68 {
69 .name = "disk-2",
70 .start = NSLU2_LED_DISK2,
71 .end = NSLU2_LED_DISK2,
72 .flags = IXP4XX_GPIO_LOW,
73 },
74};
75
76static struct platform_device nslu2_leds = {
77 .name = "IXP4XX-GPIO-LED",
78 .id = -1,
79 .num_resources = ARRAY_SIZE(nslu2_led_resources),
80 .resource = nslu2_led_resources,
81};
82#endif
83
46static struct platform_device nslu2_i2c_controller = { 84static struct platform_device nslu2_i2c_controller = {
47 .name = "IXP4XX-I2C", 85 .name = "IXP4XX-I2C",
48 .id = 0, 86 .id = 0,
@@ -102,8 +140,10 @@ static struct platform_device nslu2_uart = {
102static struct platform_device *nslu2_devices[] __initdata = { 140static struct platform_device *nslu2_devices[] __initdata = {
103 &nslu2_i2c_controller, 141 &nslu2_i2c_controller,
104 &nslu2_flash, 142 &nslu2_flash,
105 &nslu2_uart,
106 &nslu2_beeper, 143 &nslu2_beeper,
144#ifdef CONFIG_LEDS_IXP4XX
145 &nslu2_leds,
146#endif
107}; 147};
108 148
109static void nslu2_power_off(void) 149static void nslu2_power_off(void)
@@ -127,6 +167,12 @@ static void __init nslu2_init(void)
127 167
128 pm_power_off = nslu2_power_off; 168 pm_power_off = nslu2_power_off;
129 169
170 /* This is only useful on a modified machine, but it is valuable
171 * to have it first in order to see debug messages, and so that
172 * it does *not* get removed if platform_add_devices fails!
173 */
174 (void)platform_device_register(&nslu2_uart);
175
130 platform_add_devices(nslu2_devices, ARRAY_SIZE(nslu2_devices)); 176 platform_add_devices(nslu2_devices, ARRAY_SIZE(nslu2_devices));
131} 177}
132 178
diff --git a/arch/arm/mach-pnx4008/clock.c b/arch/arm/mach-pnx4008/clock.c
index 285b22f631e9..f582ed2ec43c 100644
--- a/arch/arm/mach-pnx4008/clock.c
+++ b/arch/arm/mach-pnx4008/clock.c
@@ -767,6 +767,54 @@ static struct clk *onchip_clks[] = {
767 &uart6_ck, 767 &uart6_ck,
768}; 768};
769 769
770static int local_clk_enable(struct clk *clk)
771{
772 int ret = 0;
773
774 if (!(clk->flags & FIXED_RATE) && !clk->rate && clk->set_rate
775 && clk->user_rate)
776 ret = clk->set_rate(clk, clk->user_rate);
777 return ret;
778}
779
780static void local_clk_disable(struct clk *clk)
781{
782 if (!(clk->flags & FIXED_RATE) && clk->rate && clk->set_rate)
783 clk->set_rate(clk, 0);
784}
785
786static void local_clk_unuse(struct clk *clk)
787{
788 if (clk->usecount > 0 && !(--clk->usecount)) {
789 local_clk_disable(clk);
790 if (clk->parent)
791 local_clk_unuse(clk->parent);
792 }
793}
794
795static int local_clk_use(struct clk *clk)
796{
797 int ret = 0;
798 if (clk->usecount++ == 0) {
799 if (clk->parent)
800 ret = local_clk_use(clk->parent);
801
802 if (ret != 0) {
803 clk->usecount--;
804 goto out;
805 }
806
807 ret = local_clk_enable(clk);
808
809 if (ret != 0 && clk->parent) {
810 local_clk_unuse(clk->parent);
811 clk->usecount--;
812 }
813 }
814out:
815 return ret;
816}
817
770static int local_set_rate(struct clk *clk, u32 rate) 818static int local_set_rate(struct clk *clk, u32 rate)
771{ 819{
772 int ret = -EINVAL; 820 int ret = -EINVAL;
@@ -847,28 +895,12 @@ unsigned long clk_get_rate(struct clk *clk)
847} 895}
848EXPORT_SYMBOL(clk_get_rate); 896EXPORT_SYMBOL(clk_get_rate);
849 897
850static int local_clk_enable(struct clk *clk)
851{
852 int ret = 0;
853
854 if (!(clk->flags & FIXED_RATE) && !clk->rate && clk->set_rate
855 && clk->user_rate)
856 ret = clk->set_rate(clk, clk->user_rate);
857 return ret;
858}
859
860static void local_clk_disable(struct clk *clk)
861{
862 if (!(clk->flags & FIXED_RATE) && clk->rate && clk->set_rate)
863 clk->set_rate(clk, 0);
864}
865
866int clk_enable(struct clk *clk) 898int clk_enable(struct clk *clk)
867{ 899{
868 int ret = 0; 900 int ret = 0;
869 901
870 clock_lock(); 902 clock_lock();
871 ret = local_clk_enable(clk); 903 ret = local_clk_use(clk);
872 clock_unlock(); 904 clock_unlock();
873 return ret; 905 return ret;
874} 906}
@@ -878,70 +910,11 @@ EXPORT_SYMBOL(clk_enable);
878void clk_disable(struct clk *clk) 910void clk_disable(struct clk *clk)
879{ 911{
880 clock_lock(); 912 clock_lock();
881 local_clk_disable(clk);
882 clock_unlock();
883}
884
885EXPORT_SYMBOL(clk_disable);
886
887static void local_clk_unuse(struct clk *clk)
888{
889 if (clk->usecount > 0 && !(--clk->usecount)) {
890 local_clk_disable(clk);
891 if (clk->parent)
892 local_clk_unuse(clk->parent);
893 }
894}
895
896static int local_clk_use(struct clk *clk)
897{
898 int ret = 0;
899 if (clk->usecount++ == 0) {
900 if (clk->parent)
901 ret = local_clk_use(clk->parent);
902
903 if (ret != 0) {
904 clk->usecount--;
905 goto out;
906 }
907
908 ret = local_clk_enable(clk);
909
910 if (ret != 0 && clk->parent) {
911 local_clk_unuse(clk->parent);
912 clk->usecount--;
913 }
914 }
915out:
916 return ret;
917}
918
919/* The main purpose of clk_use ans clk_unuse functions
920 * is to control switching 13MHz oscillator and PLL1 (13'MHz),
921 * so that they are disabled whenever none of PLL2-5 is using them.
922 * Although in theory these functions should work with any clock,
923 * please use them only on PLL2 - PLL5 to avoid confusion.
924 */
925int clk_use(struct clk *clk)
926{
927 int ret = 0;
928
929 clock_lock();
930 ret = local_clk_use(clk);
931 clock_unlock();
932 return ret;
933}
934EXPORT_SYMBOL(clk_use);
935
936void clk_unuse(struct clk *clk)
937{
938
939 clock_lock();
940 local_clk_unuse(clk); 913 local_clk_unuse(clk);
941 clock_unlock(); 914 clock_unlock();
942} 915}
943 916
944EXPORT_SYMBOL(clk_unuse); 917EXPORT_SYMBOL(clk_disable);
945 918
946long clk_round_rate(struct clk *clk, unsigned long rate) 919long clk_round_rate(struct clk *clk, unsigned long rate)
947{ 920{
@@ -995,7 +968,7 @@ static int __init clk_init(void)
995 __FUNCTION__, (*clkp)->name, (*clkp)->rate); 968 __FUNCTION__, (*clkp)->name, (*clkp)->rate);
996 } 969 }
997 970
998 clk_use(&ck_pll4); 971 local_clk_use(&ck_pll4);
999 972
1000 /* if ck_13MHz is not used, disable it. */ 973 /* if ck_13MHz is not used, disable it. */
1001 if (ck_13MHz.usecount == 0) 974 if (ck_13MHz.usecount == 0)
diff --git a/arch/arm/mach-pnx4008/serial.c b/arch/arm/mach-pnx4008/serial.c
index 10322384e45d..95a1b3f964a2 100644
--- a/arch/arm/mach-pnx4008/serial.c
+++ b/arch/arm/mach-pnx4008/serial.c
@@ -20,7 +20,7 @@
20 20
21#include <linux/serial_core.h> 21#include <linux/serial_core.h>
22#include <linux/serial_reg.h> 22#include <linux/serial_reg.h>
23#include <asm/arch/pm.h> 23#include <asm/arch/gpio.h>
24 24
25#include <asm/arch/clock.h> 25#include <asm/arch/clock.h>
26 26
diff --git a/arch/arm/mach-s3c2410/Kconfig b/arch/arm/mach-s3c2410/Kconfig
index 0c334136db7c..7b786d725636 100644
--- a/arch/arm/mach-s3c2410/Kconfig
+++ b/arch/arm/mach-s3c2410/Kconfig
@@ -114,9 +114,15 @@ config MACH_NEXCODER_2440
114 114
115endmenu 115endmenu
116 116
117config S3C2410_CLOCK
118 bool
119 help
120 Clock code for the S3C2410, and similar processors
121
117config CPU_S3C2410 122config CPU_S3C2410
118 bool 123 bool
119 depends on ARCH_S3C2410 124 depends on ARCH_S3C2410
125 select S3C2410_CLOCK
120 help 126 help
121 Support for S3C2410 and S3C2410A family from the S3C24XX line 127 Support for S3C2410 and S3C2410A family from the S3C24XX line
122 of Samsung Mobile CPUs. 128 of Samsung Mobile CPUs.
@@ -130,6 +136,7 @@ config CPU_S3C244X
130config CPU_S3C2440 136config CPU_S3C2440
131 bool 137 bool
132 depends on ARCH_S3C2410 138 depends on ARCH_S3C2410
139 select S3C2410_CLOCK
133 select CPU_S3C244X 140 select CPU_S3C244X
134 help 141 help
135 Support for S3C2440 Samsung Mobile CPU based systems. 142 Support for S3C2440 Samsung Mobile CPU based systems.
@@ -137,6 +144,7 @@ config CPU_S3C2440
137config CPU_S3C2442 144config CPU_S3C2442
138 bool 145 bool
139 depends on ARCH_S3C2420 146 depends on ARCH_S3C2420
147 select S3C2410_CLOCK
140 select CPU_S3C244X 148 select CPU_S3C244X
141 help 149 help
142 Support for S3C2442 Samsung Mobile CPU based systems. 150 Support for S3C2442 Samsung Mobile CPU based systems.
diff --git a/arch/arm/mach-s3c2410/Makefile b/arch/arm/mach-s3c2410/Makefile
index 5e09355cd4f4..372dbcea1434 100644
--- a/arch/arm/mach-s3c2410/Makefile
+++ b/arch/arm/mach-s3c2410/Makefile
@@ -29,6 +29,10 @@ obj-$(CONFIG_PM_SIMTEC) += pm-simtec.o
29obj-$(CONFIG_CPU_S3C244X) += s3c244x.o 29obj-$(CONFIG_CPU_S3C244X) += s3c244x.o
30obj-$(CONFIG_CPU_S3C244X) += s3c244x-irq.o 30obj-$(CONFIG_CPU_S3C244X) += s3c244x-irq.o
31 31
32# Clock control
33
34obj-$(CONFIG_S3C2410_CLOCK) += s3c2410-clock.o
35
32# S3C2440 support 36# S3C2440 support
33 37
34obj-$(CONFIG_CPU_S3C2440) += s3c2440.o s3c2440-dsc.o 38obj-$(CONFIG_CPU_S3C2440) += s3c2440.o s3c2440-dsc.o
diff --git a/arch/arm/mach-s3c2410/clock.c b/arch/arm/mach-s3c2410/clock.c
index 99d174612b53..c5c93c333ac6 100644
--- a/arch/arm/mach-s3c2410/clock.c
+++ b/arch/arm/mach-s3c2410/clock.c
@@ -3,7 +3,7 @@
3 * Copyright (c) 2004-2005 Simtec Electronics 3 * Copyright (c) 2004-2005 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk> 4 * Ben Dooks <ben@simtec.co.uk>
5 * 5 *
6 * S3C2410 Clock control support 6 * S3C24XX Core clock control support
7 * 7 *
8 * Based on, and code from linux/arch/arm/mach-versatile/clock.c 8 * Based on, and code from linux/arch/arm/mach-versatile/clock.c
9 ** 9 **
@@ -56,25 +56,6 @@ static LIST_HEAD(clocks);
56 56
57DEFINE_MUTEX(clocks_mutex); 57DEFINE_MUTEX(clocks_mutex);
58 58
59/* old functions */
60
61void inline s3c24xx_clk_enable(unsigned int clocks, unsigned int enable)
62{
63 unsigned long clkcon;
64
65 clkcon = __raw_readl(S3C2410_CLKCON);
66
67 if (enable)
68 clkcon |= clocks;
69 else
70 clkcon &= ~clocks;
71
72 /* ensure none of the special function bits set */
73 clkcon &= ~(S3C2410_CLKCON_IDLE|S3C2410_CLKCON_POWER | 3);
74
75 __raw_writel(clkcon, S3C2410_CLKCON);
76}
77
78/* enable and disable calls for use with the clk struct */ 59/* enable and disable calls for use with the clk struct */
79 60
80static int clk_null_enable(struct clk *clk, int enable) 61static int clk_null_enable(struct clk *clk, int enable)
@@ -82,12 +63,6 @@ static int clk_null_enable(struct clk *clk, int enable)
82 return 0; 63 return 0;
83} 64}
84 65
85int s3c24xx_clkcon_enable(struct clk *clk, int enable)
86{
87 s3c24xx_clk_enable(clk->ctrlbit, enable);
88 return 0;
89}
90
91/* Clock API calls */ 66/* Clock API calls */
92 67
93struct clk *clk_get(struct device *dev, const char *id) 68struct clk *clk_get(struct device *dev, const char *id)
@@ -173,8 +148,11 @@ unsigned long clk_get_rate(struct clk *clk)
173 if (clk->rate != 0) 148 if (clk->rate != 0)
174 return clk->rate; 149 return clk->rate;
175 150
176 while (clk->parent != NULL && clk->rate == 0) 151 if (clk->get_rate != NULL)
177 clk = clk->parent; 152 return (clk->get_rate)(clk);
153
154 if (clk->parent != NULL)
155 return clk_get_rate(clk->parent);
178 156
179 return clk->rate; 157 return clk->rate;
180} 158}
@@ -233,28 +211,6 @@ EXPORT_SYMBOL(clk_set_rate);
233EXPORT_SYMBOL(clk_get_parent); 211EXPORT_SYMBOL(clk_get_parent);
234EXPORT_SYMBOL(clk_set_parent); 212EXPORT_SYMBOL(clk_set_parent);
235 213
236/* base clock enable */
237
238static int s3c24xx_upll_enable(struct clk *clk, int enable)
239{
240 unsigned long clkslow = __raw_readl(S3C2410_CLKSLOW);
241 unsigned long orig = clkslow;
242
243 if (enable)
244 clkslow &= ~S3C2410_CLKSLOW_UCLK_OFF;
245 else
246 clkslow |= S3C2410_CLKSLOW_UCLK_OFF;
247
248 __raw_writel(clkslow, S3C2410_CLKSLOW);
249
250 /* if we started the UPLL, then allow to settle */
251
252 if (enable && (orig & S3C2410_CLKSLOW_UCLK_OFF))
253 udelay(200);
254
255 return 0;
256}
257
258/* base clocks */ 214/* base clocks */
259 215
260static struct clk clk_xtal = { 216static struct clk clk_xtal = {
@@ -265,15 +221,14 @@ static struct clk clk_xtal = {
265 .ctrlbit = 0, 221 .ctrlbit = 0,
266}; 222};
267 223
268static struct clk clk_upll = { 224struct clk clk_upll = {
269 .name = "upll", 225 .name = "upll",
270 .id = -1, 226 .id = -1,
271 .parent = NULL, 227 .parent = NULL,
272 .enable = s3c24xx_upll_enable,
273 .ctrlbit = 0, 228 .ctrlbit = 0,
274}; 229};
275 230
276static struct clk clk_f = { 231struct clk clk_f = {
277 .name = "fclk", 232 .name = "fclk",
278 .id = -1, 233 .id = -1,
279 .rate = 0, 234 .rate = 0,
@@ -281,7 +236,7 @@ static struct clk clk_f = {
281 .ctrlbit = 0, 236 .ctrlbit = 0,
282}; 237};
283 238
284static struct clk clk_h = { 239struct clk clk_h = {
285 .name = "hclk", 240 .name = "hclk",
286 .id = -1, 241 .id = -1,
287 .rate = 0, 242 .rate = 0,
@@ -289,7 +244,7 @@ static struct clk clk_h = {
289 .ctrlbit = 0, 244 .ctrlbit = 0,
290}; 245};
291 246
292static struct clk clk_p = { 247struct clk clk_p = {
293 .name = "pclk", 248 .name = "pclk",
294 .id = -1, 249 .id = -1,
295 .rate = 0, 250 .rate = 0,
@@ -426,108 +381,6 @@ struct clk s3c24xx_uclk = {
426 .id = -1, 381 .id = -1,
427}; 382};
428 383
429
430/* standard clock definitions */
431
432static struct clk init_clocks[] = {
433 {
434 .name = "nand",
435 .id = -1,
436 .parent = &clk_h,
437 .enable = s3c24xx_clkcon_enable,
438 .ctrlbit = S3C2410_CLKCON_NAND,
439 }, {
440 .name = "lcd",
441 .id = -1,
442 .parent = &clk_h,
443 .enable = s3c24xx_clkcon_enable,
444 .ctrlbit = S3C2410_CLKCON_LCDC,
445 }, {
446 .name = "usb-host",
447 .id = -1,
448 .parent = &clk_h,
449 .enable = s3c24xx_clkcon_enable,
450 .ctrlbit = S3C2410_CLKCON_USBH,
451 }, {
452 .name = "usb-device",
453 .id = -1,
454 .parent = &clk_h,
455 .enable = s3c24xx_clkcon_enable,
456 .ctrlbit = S3C2410_CLKCON_USBD,
457 }, {
458 .name = "timers",
459 .id = -1,
460 .parent = &clk_p,
461 .enable = s3c24xx_clkcon_enable,
462 .ctrlbit = S3C2410_CLKCON_PWMT,
463 }, {
464 .name = "sdi",
465 .id = -1,
466 .parent = &clk_p,
467 .enable = s3c24xx_clkcon_enable,
468 .ctrlbit = S3C2410_CLKCON_SDI,
469 }, {
470 .name = "uart",
471 .id = 0,
472 .parent = &clk_p,
473 .enable = s3c24xx_clkcon_enable,
474 .ctrlbit = S3C2410_CLKCON_UART0,
475 }, {
476 .name = "uart",
477 .id = 1,
478 .parent = &clk_p,
479 .enable = s3c24xx_clkcon_enable,
480 .ctrlbit = S3C2410_CLKCON_UART1,
481 }, {
482 .name = "uart",
483 .id = 2,
484 .parent = &clk_p,
485 .enable = s3c24xx_clkcon_enable,
486 .ctrlbit = S3C2410_CLKCON_UART2,
487 }, {
488 .name = "gpio",
489 .id = -1,
490 .parent = &clk_p,
491 .enable = s3c24xx_clkcon_enable,
492 .ctrlbit = S3C2410_CLKCON_GPIO,
493 }, {
494 .name = "rtc",
495 .id = -1,
496 .parent = &clk_p,
497 .enable = s3c24xx_clkcon_enable,
498 .ctrlbit = S3C2410_CLKCON_RTC,
499 }, {
500 .name = "adc",
501 .id = -1,
502 .parent = &clk_p,
503 .enable = s3c24xx_clkcon_enable,
504 .ctrlbit = S3C2410_CLKCON_ADC,
505 }, {
506 .name = "i2c",
507 .id = -1,
508 .parent = &clk_p,
509 .enable = s3c24xx_clkcon_enable,
510 .ctrlbit = S3C2410_CLKCON_IIC,
511 }, {
512 .name = "iis",
513 .id = -1,
514 .parent = &clk_p,
515 .enable = s3c24xx_clkcon_enable,
516 .ctrlbit = S3C2410_CLKCON_IIS,
517 }, {
518 .name = "spi",
519 .id = -1,
520 .parent = &clk_p,
521 .enable = s3c24xx_clkcon_enable,
522 .ctrlbit = S3C2410_CLKCON_SPI,
523 }, {
524 .name = "watchdog",
525 .id = -1,
526 .parent = &clk_p,
527 .ctrlbit = 0,
528 }
529};
530
531/* initialise the clock system */ 384/* initialise the clock system */
532 385
533int s3c24xx_register_clock(struct clk *clk) 386int s3c24xx_register_clock(struct clk *clk)
@@ -537,14 +390,6 @@ int s3c24xx_register_clock(struct clk *clk)
537 if (clk->enable == NULL) 390 if (clk->enable == NULL)
538 clk->enable = clk_null_enable; 391 clk->enable = clk_null_enable;
539 392
540 /* if this is a standard clock, set the usage state */
541
542 if (clk->ctrlbit && clk->enable == s3c24xx_clkcon_enable) {
543 unsigned long clkcon = __raw_readl(S3C2410_CLKCON);
544
545 clk->usage = (clkcon & clk->ctrlbit) ? 1 : 0;
546 }
547
548 /* add to the list of available clocks */ 393 /* add to the list of available clocks */
549 394
550 mutex_lock(&clocks_mutex); 395 mutex_lock(&clocks_mutex);
@@ -561,44 +406,17 @@ int __init s3c24xx_setup_clocks(unsigned long xtal,
561 unsigned long hclk, 406 unsigned long hclk,
562 unsigned long pclk) 407 unsigned long pclk)
563{ 408{
564 unsigned long upllcon = __raw_readl(S3C2410_UPLLCON); 409 printk(KERN_INFO "S3C24XX Clocks, (c) 2004 Simtec Electronics\n");
565 unsigned long clkslow = __raw_readl(S3C2410_CLKSLOW);
566 struct clk *clkp = init_clocks;
567 int ptr;
568 int ret;
569
570 printk(KERN_INFO "S3C2410 Clocks, (c) 2004 Simtec Electronics\n");
571 410
572 /* initialise the main system clocks */ 411 /* initialise the main system clocks */
573 412
574 clk_xtal.rate = xtal; 413 clk_xtal.rate = xtal;
575 clk_upll.rate = s3c2410_get_pll(upllcon, xtal); 414 clk_upll.rate = s3c2410_get_pll(__raw_readl(S3C2410_UPLLCON), xtal);
576 415
577 clk_h.rate = hclk; 416 clk_h.rate = hclk;
578 clk_p.rate = pclk; 417 clk_p.rate = pclk;
579 clk_f.rate = fclk; 418 clk_f.rate = fclk;
580 419
581 /* We must be careful disabling the clocks we are not intending to
582 * be using at boot time, as subsytems such as the LCD which do
583 * their own DMA requests to the bus can cause the system to lockup
584 * if they where in the middle of requesting bus access.
585 *
586 * Disabling the LCD clock if the LCD is active is very dangerous,
587 * and therefore the bootloader should be careful to not enable
588 * the LCD clock if it is not needed.
589 */
590
591 mutex_lock(&clocks_mutex);
592
593 s3c24xx_clk_enable(S3C2410_CLKCON_NAND, 0);
594 s3c24xx_clk_enable(S3C2410_CLKCON_USBH, 0);
595 s3c24xx_clk_enable(S3C2410_CLKCON_USBD, 0);
596 s3c24xx_clk_enable(S3C2410_CLKCON_ADC, 0);
597 s3c24xx_clk_enable(S3C2410_CLKCON_IIC, 0);
598 s3c24xx_clk_enable(S3C2410_CLKCON_SPI, 0);
599
600 mutex_unlock(&clocks_mutex);
601
602 /* assume uart clocks are correctly setup */ 420 /* assume uart clocks are correctly setup */
603 421
604 /* register our clocks */ 422 /* register our clocks */
@@ -618,27 +436,5 @@ int __init s3c24xx_setup_clocks(unsigned long xtal,
618 if (s3c24xx_register_clock(&clk_p) < 0) 436 if (s3c24xx_register_clock(&clk_p) < 0)
619 printk(KERN_ERR "failed to register cpu pclk\n"); 437 printk(KERN_ERR "failed to register cpu pclk\n");
620 438
621
622 if (s3c24xx_register_clock(&clk_usb_bus) < 0)
623 printk(KERN_ERR "failed to register usb bus clock\n");
624
625 /* register clocks from clock array */
626
627 for (ptr = 0; ptr < ARRAY_SIZE(init_clocks); ptr++, clkp++) {
628 ret = s3c24xx_register_clock(clkp);
629 if (ret < 0) {
630 printk(KERN_ERR "Failed to register clock %s (%d)\n",
631 clkp->name, ret);
632 }
633 }
634
635 /* show the clock-slow value */
636
637 printk("CLOCK: Slow mode (%ld.%ld MHz), %s, MPLL %s, UPLL %s\n",
638 print_mhz(xtal / ( 2 * S3C2410_CLKSLOW_GET_SLOWVAL(clkslow))),
639 (clkslow & S3C2410_CLKSLOW_SLOW) ? "slow" : "fast",
640 (clkslow & S3C2410_CLKSLOW_MPLL_OFF) ? "off" : "on",
641 (clkslow & S3C2410_CLKSLOW_UCLK_OFF) ? "off" : "on");
642
643 return 0; 439 return 0;
644} 440}
diff --git a/arch/arm/mach-s3c2410/clock.h b/arch/arm/mach-s3c2410/clock.h
index 01bb458bf8eb..9456c81eb5d3 100644
--- a/arch/arm/mach-s3c2410/clock.h
+++ b/arch/arm/mach-s3c2410/clock.h
@@ -22,6 +22,7 @@ struct clk {
22 22
23 int (*enable)(struct clk *, int enable); 23 int (*enable)(struct clk *, int enable);
24 int (*set_rate)(struct clk *c, unsigned long rate); 24 int (*set_rate)(struct clk *c, unsigned long rate);
25 unsigned long (*get_rate)(struct clk *c);
25 unsigned long (*round_rate)(struct clk *c, unsigned long rate); 26 unsigned long (*round_rate)(struct clk *c, unsigned long rate);
26 int (*set_parent)(struct clk *c, struct clk *parent); 27 int (*set_parent)(struct clk *c, struct clk *parent);
27}; 28};
@@ -36,6 +37,13 @@ extern struct clk s3c24xx_uclk;
36 37
37extern struct clk clk_usb_bus; 38extern struct clk clk_usb_bus;
38 39
40/* core clock support */
41
42extern struct clk clk_f;
43extern struct clk clk_h;
44extern struct clk clk_p;
45extern struct clk clk_upll;
46
39/* exports for arch/arm/mach-s3c2410 47/* exports for arch/arm/mach-s3c2410
40 * 48 *
41 * Please DO NOT use these outside of arch/arm/mach-s3c2410 49 * Please DO NOT use these outside of arch/arm/mach-s3c2410
@@ -43,7 +51,8 @@ extern struct clk clk_usb_bus;
43 51
44extern struct mutex clocks_mutex; 52extern struct mutex clocks_mutex;
45 53
46extern int s3c24xx_clkcon_enable(struct clk *clk, int enable); 54extern int s3c2410_clkcon_enable(struct clk *clk, int enable);
55
47extern int s3c24xx_register_clock(struct clk *clk); 56extern int s3c24xx_register_clock(struct clk *clk);
48 57
49extern int s3c24xx_setup_clocks(unsigned long xtal, 58extern int s3c24xx_setup_clocks(unsigned long xtal,
diff --git a/arch/arm/mach-s3c2410/cpu.h b/arch/arm/mach-s3c2410/cpu.h
index 40862899b2f1..21c62dc29bb2 100644
--- a/arch/arm/mach-s3c2410/cpu.h
+++ b/arch/arm/mach-s3c2410/cpu.h
@@ -73,5 +73,6 @@ extern struct sys_timer s3c24xx_timer;
73 73
74/* system device classes */ 74/* system device classes */
75 75
76extern struct sysdev_class s3c2410_sysclass;
76extern struct sysdev_class s3c2440_sysclass; 77extern struct sysdev_class s3c2440_sysclass;
77extern struct sysdev_class s3c2442_sysclass; 78extern struct sysdev_class s3c2442_sysclass;
diff --git a/arch/arm/mach-s3c2410/s3c2410-clock.c b/arch/arm/mach-s3c2410/s3c2410-clock.c
new file mode 100644
index 000000000000..fd17c60e1132
--- /dev/null
+++ b/arch/arm/mach-s3c2410/s3c2410-clock.c
@@ -0,0 +1,263 @@
1/* linux/arch/arm/mach-s3c2410/clock.c
2 *
3 * Copyright (c) 2006 Simtec Electronics
4 * Ben Dooks <ben@simtec.co.uk>
5 *
6 * S3C2410,S3C2440,S3C2442 Clock control support
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21*/
22
23#include <linux/init.h>
24#include <linux/module.h>
25#include <linux/kernel.h>
26#include <linux/list.h>
27#include <linux/errno.h>
28#include <linux/err.h>
29#include <linux/sysdev.h>
30#include <linux/clk.h>
31#include <linux/mutex.h>
32#include <linux/delay.h>
33
34#include <asm/hardware.h>
35#include <asm/io.h>
36
37#include <asm/arch/regs-clock.h>
38#include <asm/arch/regs-gpio.h>
39
40#include "clock.h"
41#include "cpu.h"
42
43int s3c2410_clkcon_enable(struct clk *clk, int enable)
44{
45 unsigned int clocks = clk->ctrlbit;
46 unsigned long clkcon;
47
48 clkcon = __raw_readl(S3C2410_CLKCON);
49
50 if (enable)
51 clkcon |= clocks;
52 else
53 clkcon &= ~clocks;
54
55 /* ensure none of the special function bits set */
56 clkcon &= ~(S3C2410_CLKCON_IDLE|S3C2410_CLKCON_POWER);
57
58 __raw_writel(clkcon, S3C2410_CLKCON);
59
60 return 0;
61}
62
63static int s3c2410_upll_enable(struct clk *clk, int enable)
64{
65 unsigned long clkslow = __raw_readl(S3C2410_CLKSLOW);
66 unsigned long orig = clkslow;
67
68 if (enable)
69 clkslow &= ~S3C2410_CLKSLOW_UCLK_OFF;
70 else
71 clkslow |= S3C2410_CLKSLOW_UCLK_OFF;
72
73 __raw_writel(clkslow, S3C2410_CLKSLOW);
74
75 /* if we started the UPLL, then allow to settle */
76
77 if (enable && (orig & S3C2410_CLKSLOW_UCLK_OFF))
78 udelay(200);
79
80 return 0;
81}
82
83/* standard clock definitions */
84
85static struct clk init_clocks_disable[] = {
86 {
87 .name = "nand",
88 .id = -1,
89 .parent = &clk_h,
90 .enable = s3c2410_clkcon_enable,
91 .ctrlbit = S3C2410_CLKCON_NAND,
92 }, {
93 .name = "sdi",
94 .id = -1,
95 .parent = &clk_p,
96 .enable = s3c2410_clkcon_enable,
97 .ctrlbit = S3C2410_CLKCON_SDI,
98 }, {
99 .name = "adc",
100 .id = -1,
101 .parent = &clk_p,
102 .enable = s3c2410_clkcon_enable,
103 .ctrlbit = S3C2410_CLKCON_ADC,
104 }, {
105 .name = "i2c",
106 .id = -1,
107 .parent = &clk_p,
108 .enable = s3c2410_clkcon_enable,
109 .ctrlbit = S3C2410_CLKCON_IIC,
110 }, {
111 .name = "iis",
112 .id = -1,
113 .parent = &clk_p,
114 .enable = s3c2410_clkcon_enable,
115 .ctrlbit = S3C2410_CLKCON_IIS,
116 }, {
117 .name = "spi",
118 .id = -1,
119 .parent = &clk_p,
120 .enable = s3c2410_clkcon_enable,
121 .ctrlbit = S3C2410_CLKCON_SPI,
122 }
123};
124
125static struct clk init_clocks[] = {
126 {
127 .name = "lcd",
128 .id = -1,
129 .parent = &clk_h,
130 .enable = s3c2410_clkcon_enable,
131 .ctrlbit = S3C2410_CLKCON_LCDC,
132 }, {
133 .name = "gpio",
134 .id = -1,
135 .parent = &clk_p,
136 .enable = s3c2410_clkcon_enable,
137 .ctrlbit = S3C2410_CLKCON_GPIO,
138 }, {
139 .name = "usb-host",
140 .id = -1,
141 .parent = &clk_h,
142 .enable = s3c2410_clkcon_enable,
143 .ctrlbit = S3C2410_CLKCON_USBH,
144 }, {
145 .name = "usb-device",
146 .id = -1,
147 .parent = &clk_h,
148 .enable = s3c2410_clkcon_enable,
149 .ctrlbit = S3C2410_CLKCON_USBD,
150 }, {
151 .name = "timers",
152 .id = -1,
153 .parent = &clk_p,
154 .enable = s3c2410_clkcon_enable,
155 .ctrlbit = S3C2410_CLKCON_PWMT,
156 }, {
157 .name = "uart",
158 .id = 0,
159 .parent = &clk_p,
160 .enable = s3c2410_clkcon_enable,
161 .ctrlbit = S3C2410_CLKCON_UART0,
162 }, {
163 .name = "uart",
164 .id = 1,
165 .parent = &clk_p,
166 .enable = s3c2410_clkcon_enable,
167 .ctrlbit = S3C2410_CLKCON_UART1,
168 }, {
169 .name = "uart",
170 .id = 2,
171 .parent = &clk_p,
172 .enable = s3c2410_clkcon_enable,
173 .ctrlbit = S3C2410_CLKCON_UART2,
174 }, {
175 .name = "rtc",
176 .id = -1,
177 .parent = &clk_p,
178 .enable = s3c2410_clkcon_enable,
179 .ctrlbit = S3C2410_CLKCON_RTC,
180 }, {
181 .name = "watchdog",
182 .id = -1,
183 .parent = &clk_p,
184 .ctrlbit = 0,
185 }
186};
187
188/* s3c2410_baseclk_add()
189 *
190 * Add all the clocks used by the s3c2410 or compatible CPUs
191 * such as the S3C2440 and S3C2442.
192 *
193 * We cannot use a system device as we are needed before any
194 * of the init-calls that initialise the devices are actually
195 * done.
196*/
197
198int __init s3c2410_baseclk_add(void)
199{
200 unsigned long clkslow = __raw_readl(S3C2410_CLKSLOW);
201 unsigned long clkcon = __raw_readl(S3C2410_CLKCON);
202 struct clk *clkp;
203 struct clk *xtal;
204 int ret;
205 int ptr;
206
207 clk_upll.enable = s3c2410_upll_enable;
208
209 if (s3c24xx_register_clock(&clk_usb_bus) < 0)
210 printk(KERN_ERR "failed to register usb bus clock\n");
211
212 /* register clocks from clock array */
213
214 clkp = init_clocks;
215 for (ptr = 0; ptr < ARRAY_SIZE(init_clocks); ptr++, clkp++) {
216 /* ensure that we note the clock state */
217
218 clkp->usage = clkcon & clkp->ctrlbit ? 1 : 0;
219
220 ret = s3c24xx_register_clock(clkp);
221 if (ret < 0) {
222 printk(KERN_ERR "Failed to register clock %s (%d)\n",
223 clkp->name, ret);
224 }
225 }
226
227 /* We must be careful disabling the clocks we are not intending to
228 * be using at boot time, as subsytems such as the LCD which do
229 * their own DMA requests to the bus can cause the system to lockup
230 * if they where in the middle of requesting bus access.
231 *
232 * Disabling the LCD clock if the LCD is active is very dangerous,
233 * and therefore the bootloader should be careful to not enable
234 * the LCD clock if it is not needed.
235 */
236
237 /* install (and disable) the clocks we do not need immediately */
238
239 clkp = init_clocks_disable;
240 for (ptr = 0; ptr < ARRAY_SIZE(init_clocks_disable); ptr++, clkp++) {
241
242 ret = s3c24xx_register_clock(clkp);
243 if (ret < 0) {
244 printk(KERN_ERR "Failed to register clock %s (%d)\n",
245 clkp->name, ret);
246 }
247
248 s3c2410_clkcon_enable(clkp, 0);
249 }
250
251 /* show the clock-slow value */
252
253 xtal = clk_get(NULL, "xtal");
254
255 printk("CLOCK: Slow mode (%ld.%ld MHz), %s, MPLL %s, UPLL %s\n",
256 print_mhz(clk_get_rate(xtal) /
257 ( 2 * S3C2410_CLKSLOW_GET_SLOWVAL(clkslow))),
258 (clkslow & S3C2410_CLKSLOW_SLOW) ? "slow" : "fast",
259 (clkslow & S3C2410_CLKSLOW_MPLL_OFF) ? "off" : "on",
260 (clkslow & S3C2410_CLKSLOW_UCLK_OFF) ? "off" : "on");
261
262 return 0;
263}
diff --git a/arch/arm/mach-s3c2410/s3c2410.c b/arch/arm/mach-s3c2410/s3c2410.c
index 0852e87a79c4..a110cff9cf6b 100644
--- a/arch/arm/mach-s3c2410/s3c2410.c
+++ b/arch/arm/mach-s3c2410/s3c2410.c
@@ -27,6 +27,7 @@
27#include <linux/list.h> 27#include <linux/list.h>
28#include <linux/timer.h> 28#include <linux/timer.h>
29#include <linux/init.h> 29#include <linux/init.h>
30#include <linux/sysdev.h>
30#include <linux/platform_device.h> 31#include <linux/platform_device.h>
31 32
32#include <asm/mach/arch.h> 33#include <asm/mach/arch.h>
@@ -108,11 +109,33 @@ void __init s3c2410_init_clocks(int xtal)
108 */ 109 */
109 110
110 s3c24xx_setup_clocks(xtal, fclk, hclk, pclk); 111 s3c24xx_setup_clocks(xtal, fclk, hclk, pclk);
112 s3c2410_baseclk_add();
111} 113}
112 114
115struct sysdev_class s3c2410_sysclass = {
116 set_kset_name("s3c2410-core"),
117};
118
119static struct sys_device s3c2410_sysdev = {
120 .cls = &s3c2410_sysclass,
121};
122
123/* need to register class before we actually register the device, and
124 * we also need to ensure that it has been initialised before any of the
125 * drivers even try to use it (even if not on an s3c2440 based system)
126 * as a driver which may support both 2410 and 2440 may try and use it.
127*/
128
129static int __init s3c2410_core_init(void)
130{
131 return sysdev_class_register(&s3c2410_sysclass);
132}
133
134core_initcall(s3c2410_core_init);
135
113int __init s3c2410_init(void) 136int __init s3c2410_init(void)
114{ 137{
115 printk("S3C2410: Initialising architecture\n"); 138 printk("S3C2410: Initialising architecture\n");
116 139
117 return 0; 140 return sysdev_register(&s3c2410_sysdev);
118} 141}
diff --git a/arch/arm/mach-s3c2410/s3c2410.h b/arch/arm/mach-s3c2410/s3c2410.h
index 4d5312a48209..73f1a2474a61 100644
--- a/arch/arm/mach-s3c2410/s3c2410.h
+++ b/arch/arm/mach-s3c2410/s3c2410.h
@@ -29,6 +29,8 @@ extern void s3c2410_init_uarts(struct s3c2410_uartcfg *cfg, int no);
29 29
30extern void s3c2410_init_clocks(int xtal); 30extern void s3c2410_init_clocks(int xtal);
31 31
32extern int s3c2410_baseclk_add(void);
33
32#else 34#else
33#define s3c2410_init_clocks NULL 35#define s3c2410_init_clocks NULL
34#define s3c2410_init_uarts NULL 36#define s3c2410_init_uarts NULL
diff --git a/arch/arm/mach-s3c2410/s3c2440-clock.c b/arch/arm/mach-s3c2410/s3c2440-clock.c
index d7a30ed6c327..15796864d010 100644
--- a/arch/arm/mach-s3c2410/s3c2440-clock.c
+++ b/arch/arm/mach-s3c2410/s3c2440-clock.c
@@ -91,7 +91,7 @@ static int s3c2440_camif_upll_setrate(struct clk *clk, unsigned long rate)
91static struct clk s3c2440_clk_cam = { 91static struct clk s3c2440_clk_cam = {
92 .name = "camif", 92 .name = "camif",
93 .id = -1, 93 .id = -1,
94 .enable = s3c24xx_clkcon_enable, 94 .enable = s3c2410_clkcon_enable,
95 .ctrlbit = S3C2440_CLKCON_CAMERA, 95 .ctrlbit = S3C2440_CLKCON_CAMERA,
96}; 96};
97 97
@@ -105,7 +105,7 @@ static struct clk s3c2440_clk_cam_upll = {
105static struct clk s3c2440_clk_ac97 = { 105static struct clk s3c2440_clk_ac97 = {
106 .name = "ac97", 106 .name = "ac97",
107 .id = -1, 107 .id = -1,
108 .enable = s3c24xx_clkcon_enable, 108 .enable = s3c2410_clkcon_enable,
109 .ctrlbit = S3C2440_CLKCON_CAMERA, 109 .ctrlbit = S3C2440_CLKCON_CAMERA,
110}; 110};
111 111
diff --git a/arch/arm/mach-s3c2410/s3c2442-clock.c b/arch/arm/mach-s3c2410/s3c2442-clock.c
index 5b7b301eb522..d9f54b5cab7f 100644
--- a/arch/arm/mach-s3c2410/s3c2442-clock.c
+++ b/arch/arm/mach-s3c2410/s3c2442-clock.c
@@ -102,7 +102,7 @@ static int s3c2442_camif_upll_setrate(struct clk *clk, unsigned long rate)
102static struct clk s3c2442_clk_cam = { 102static struct clk s3c2442_clk_cam = {
103 .name = "camif", 103 .name = "camif",
104 .id = -1, 104 .id = -1,
105 .enable = s3c24xx_clkcon_enable, 105 .enable = s3c2410_clkcon_enable,
106 .ctrlbit = S3C2440_CLKCON_CAMERA, 106 .ctrlbit = S3C2440_CLKCON_CAMERA,
107}; 107};
108 108
diff --git a/arch/arm/mach-s3c2410/s3c244x.c b/arch/arm/mach-s3c2410/s3c244x.c
index 96852a7000db..838bc525e836 100644
--- a/arch/arm/mach-s3c2410/s3c244x.c
+++ b/arch/arm/mach-s3c2410/s3c244x.c
@@ -34,6 +34,7 @@
34#include <asm/arch/regs-gpioj.h> 34#include <asm/arch/regs-gpioj.h>
35#include <asm/arch/regs-dsc.h> 35#include <asm/arch/regs-dsc.h>
36 36
37#include "s3c2410.h"
37#include "s3c2440.h" 38#include "s3c2440.h"
38#include "s3c244x.h" 39#include "s3c244x.h"
39#include "clock.h" 40#include "clock.h"
@@ -118,6 +119,7 @@ void __init s3c244x_init_clocks(int xtal)
118 */ 119 */
119 120
120 s3c24xx_setup_clocks(xtal, fclk, hclk, pclk); 121 s3c24xx_setup_clocks(xtal, fclk, hclk, pclk);
122 s3c2410_baseclk_add();
121} 123}
122 124
123#ifdef CONFIG_PM 125#ifdef CONFIG_PM
diff --git a/arch/arm/nwfpe/fpmodule.c b/arch/arm/nwfpe/fpmodule.c
index 2dfe1ac42ee8..7d977d23f026 100644
--- a/arch/arm/nwfpe/fpmodule.c
+++ b/arch/arm/nwfpe/fpmodule.c
@@ -33,7 +33,8 @@
33#include <linux/signal.h> 33#include <linux/signal.h>
34#include <linux/sched.h> 34#include <linux/sched.h>
35#include <linux/init.h> 35#include <linux/init.h>
36/* XXX */ 36
37#include <asm/thread_notify.h>
37 38
38#include "softfloat.h" 39#include "softfloat.h"
39#include "fpopcode.h" 40#include "fpopcode.h"
@@ -56,16 +57,28 @@ void fp_send_sig(unsigned long sig, struct task_struct *p, int priv);
56extern char fpe_type[]; 57extern char fpe_type[];
57#endif 58#endif
58 59
60static int nwfpe_notify(struct notifier_block *self, unsigned long cmd, void *v)
61{
62 struct thread_info *thread = v;
63
64 if (cmd == THREAD_NOTIFY_FLUSH)
65 nwfpe_init_fpa(&thread->fpstate);
66
67 return NOTIFY_DONE;
68}
69
70static struct notifier_block nwfpe_notifier_block = {
71 .notifier_call = nwfpe_notify,
72};
73
59/* kernel function prototypes required */ 74/* kernel function prototypes required */
60void fp_setup(void); 75void fp_setup(void);
61 76
62/* external declarations for saved kernel symbols */ 77/* external declarations for saved kernel symbols */
63extern void (*kern_fp_enter)(void); 78extern void (*kern_fp_enter)(void);
64extern void (*fp_init)(union fp_state *);
65 79
66/* Original value of fp_enter from kernel before patched by fpe_init. */ 80/* Original value of fp_enter from kernel before patched by fpe_init. */
67static void (*orig_fp_enter)(void); 81static void (*orig_fp_enter)(void);
68static void (*orig_fp_init)(union fp_state *);
69 82
70/* forward declarations */ 83/* forward declarations */
71extern void nwfpe_enter(void); 84extern void nwfpe_enter(void);
@@ -88,20 +101,20 @@ static int __init fpe_init(void)
88 printk(KERN_WARNING "NetWinder Floating Point Emulator V0.97 (" 101 printk(KERN_WARNING "NetWinder Floating Point Emulator V0.97 ("
89 NWFPE_BITS " precision)\n"); 102 NWFPE_BITS " precision)\n");
90 103
104 thread_register_notifier(&nwfpe_notifier_block);
105
91 /* Save pointer to the old FP handler and then patch ourselves in */ 106 /* Save pointer to the old FP handler and then patch ourselves in */
92 orig_fp_enter = kern_fp_enter; 107 orig_fp_enter = kern_fp_enter;
93 orig_fp_init = fp_init;
94 kern_fp_enter = nwfpe_enter; 108 kern_fp_enter = nwfpe_enter;
95 fp_init = nwfpe_init_fpa;
96 109
97 return 0; 110 return 0;
98} 111}
99 112
100static void __exit fpe_exit(void) 113static void __exit fpe_exit(void)
101{ 114{
115 thread_unregister_notifier(&nwfpe_notifier_block);
102 /* Restore the values we saved earlier. */ 116 /* Restore the values we saved earlier. */
103 kern_fp_enter = orig_fp_enter; 117 kern_fp_enter = orig_fp_enter;
104 fp_init = orig_fp_init;
105} 118}
106 119
107/* 120/*
diff --git a/arch/arm/plat-omap/timer32k.c b/arch/arm/plat-omap/timer32k.c
index b2a943bf11ef..3461a6c9665c 100644
--- a/arch/arm/plat-omap/timer32k.c
+++ b/arch/arm/plat-omap/timer32k.c
@@ -210,7 +210,8 @@ static irqreturn_t omap_32k_timer_interrupt(int irq, void *dev_id,
210 210
211 now = omap_32k_sync_timer_read(); 211 now = omap_32k_sync_timer_read();
212 212
213 while (now - omap_32k_last_tick >= OMAP_32K_TICKS_PER_HZ) { 213 while ((signed long)(now - omap_32k_last_tick)
214 >= OMAP_32K_TICKS_PER_HZ) {
214 omap_32k_last_tick += OMAP_32K_TICKS_PER_HZ; 215 omap_32k_last_tick += OMAP_32K_TICKS_PER_HZ;
215 timer_tick(regs); 216 timer_tick(regs);
216 } 217 }
diff --git a/arch/arm/vfp/Makefile b/arch/arm/vfp/Makefile
index afabac31dd1d..7e136e77971a 100644
--- a/arch/arm/vfp/Makefile
+++ b/arch/arm/vfp/Makefile
@@ -7,6 +7,9 @@
7# EXTRA_CFLAGS := -DDEBUG 7# EXTRA_CFLAGS := -DDEBUG
8# EXTRA_AFLAGS := -DDEBUG 8# EXTRA_AFLAGS := -DDEBUG
9 9
10AFLAGS :=$(AFLAGS:-msoft-float=-Wa,-mfpu=softvfp+vfp)
11LDFLAGS +=--no-warn-mismatch
12
10obj-y += vfp.o 13obj-y += vfp.o
11 14
12vfp-$(CONFIG_VFP) += entry.o vfpmodule.o vfphw.o vfpsingle.o vfpdouble.o 15vfp-$(CONFIG_VFP) += vfpmodule.o entry.o vfphw.o vfpsingle.o vfpdouble.o
diff --git a/arch/arm/vfp/vfphw.S b/arch/arm/vfp/vfphw.S
index a3f65b47aea9..eb683cd77163 100644
--- a/arch/arm/vfp/vfphw.S
+++ b/arch/arm/vfp/vfphw.S
@@ -192,7 +192,7 @@ vfp_get_double:
192 add pc, pc, r0, lsl #3 192 add pc, pc, r0, lsl #3
193 mov r0, r0 193 mov r0, r0
194 .irp dr,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15 194 .irp dr,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
195 mrrc p11, 1, r0, r1, c\dr @ fmrrd r0, r1, d\dr 195 fmrrd r0, r1, d\dr
196 mov pc, lr 196 mov pc, lr
197 .endr 197 .endr
198 198
@@ -206,6 +206,6 @@ vfp_put_double:
206 add pc, pc, r0, lsl #3 206 add pc, pc, r0, lsl #3
207 mov r0, r0 207 mov r0, r0
208 .irp dr,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15 208 .irp dr,0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15
209 mcrr p11, 1, r1, r2, c\dr @ fmdrr r1, r2, d\dr 209 fmdrr d\dr, r1, r2
210 mov pc, lr 210 mov pc, lr
211 .endr 211 .endr
diff --git a/arch/arm/vfp/vfpmodule.c b/arch/arm/vfp/vfpmodule.c
index 03486be04193..2476f4c2e760 100644
--- a/arch/arm/vfp/vfpmodule.c
+++ b/arch/arm/vfp/vfpmodule.c
@@ -15,6 +15,8 @@
15#include <linux/signal.h> 15#include <linux/signal.h>
16#include <linux/sched.h> 16#include <linux/sched.h>
17#include <linux/init.h> 17#include <linux/init.h>
18
19#include <asm/thread_notify.h>
18#include <asm/vfp.h> 20#include <asm/vfp.h>
19 21
20#include "vfpinstr.h" 22#include "vfpinstr.h"
@@ -36,38 +38,55 @@ union vfp_state *last_VFP_context;
36 */ 38 */
37unsigned int VFP_arch; 39unsigned int VFP_arch;
38 40
39/* 41static int vfp_notifier(struct notifier_block *self, unsigned long cmd, void *v)
40 * Per-thread VFP initialisation.
41 */
42void vfp_flush_thread(union vfp_state *vfp)
43{ 42{
44 memset(vfp, 0, sizeof(union vfp_state)); 43 struct thread_info *thread = v;
44 union vfp_state *vfp = &thread->vfpstate;
45 45
46 vfp->hard.fpexc = FPEXC_ENABLE; 46 switch (cmd) {
47 vfp->hard.fpscr = FPSCR_ROUND_NEAREST; 47 case THREAD_NOTIFY_FLUSH:
48 /*
49 * Per-thread VFP initialisation.
50 */
51 memset(vfp, 0, sizeof(union vfp_state));
48 52
49 /* 53 vfp->hard.fpexc = FPEXC_ENABLE;
50 * Disable VFP to ensure we initialise it first. 54 vfp->hard.fpscr = FPSCR_ROUND_NEAREST;
51 */
52 fmxr(FPEXC, fmrx(FPEXC) & ~FPEXC_ENABLE);
53 55
54 /* 56 /*
55 * Ensure we don't try to overwrite our newly initialised 57 * Disable VFP to ensure we initialise it first.
56 * state information on the first fault. 58 */
57 */ 59 fmxr(FPEXC, fmrx(FPEXC) & ~FPEXC_ENABLE);
58 if (last_VFP_context == vfp)
59 last_VFP_context = NULL;
60}
61 60
62/* 61 /*
63 * Per-thread VFP cleanup. 62 * FALLTHROUGH: Ensure we don't try to overwrite our newly
64 */ 63 * initialised state information on the first fault.
65void vfp_release_thread(union vfp_state *vfp) 64 */
66{ 65
67 if (last_VFP_context == vfp) 66 case THREAD_NOTIFY_RELEASE:
68 last_VFP_context = NULL; 67 /*
68 * Per-thread VFP cleanup.
69 */
70 if (last_VFP_context == vfp)
71 last_VFP_context = NULL;
72 break;
73
74 case THREAD_NOTIFY_SWITCH:
75 /*
76 * Always disable VFP so we can lazily save/restore the
77 * old state.
78 */
79 fmxr(FPEXC, fmrx(FPEXC) & ~FPEXC_ENABLE);
80 break;
81 }
82
83 return NOTIFY_DONE;
69} 84}
70 85
86static struct notifier_block vfp_notifier_block = {
87 .notifier_call = vfp_notifier,
88};
89
71/* 90/*
72 * Raise a SIGFPE for the current process. 91 * Raise a SIGFPE for the current process.
73 * sicode describes the signal being raised. 92 * sicode describes the signal being raised.
@@ -281,6 +300,8 @@ static int __init vfp_init(void)
281 (vfpsid & FPSID_VARIANT_MASK) >> FPSID_VARIANT_BIT, 300 (vfpsid & FPSID_VARIANT_MASK) >> FPSID_VARIANT_BIT,
282 (vfpsid & FPSID_REV_MASK) >> FPSID_REV_BIT); 301 (vfpsid & FPSID_REV_MASK) >> FPSID_REV_BIT);
283 vfp_vector = vfp_support_entry; 302 vfp_vector = vfp_support_entry;
303
304 thread_register_notifier(&vfp_notifier_block);
284 } 305 }
285 return 0; 306 return 0;
286} 307}