static void s3c2410_pm_prepare(void) { /* ensure at least GSTATUS3 has the resume address */ __raw_writel(virt_to_phys(s3c_cpu_resume), S3C2410_GSTATUS3); S3C_PMDBG("GSTATUS3 0x%08x\n", __raw_readl(S3C2410_GSTATUS3)); S3C_PMDBG("GSTATUS4 0x%08x\n", __raw_readl(S3C2410_GSTATUS4)); if (machine_is_h1940()) { void *base = phys_to_virt(H1940_SUSPEND_CHECK); unsigned long ptr; unsigned long calc = 0; /* generate check for the bootloader to check on resume */ for (ptr = 0; ptr < 0x40000; ptr += 0x400) calc += __raw_readl(base+ptr); __raw_writel(calc, phys_to_virt(H1940_SUSPEND_CHECKSUM)); } /* RX3715 and RX1950 use similar to H1940 code and the * same offsets for resume and checksum pointers */ if (machine_is_rx3715() || machine_is_rx1950()) { void *base = phys_to_virt(H1940_SUSPEND_CHECK); unsigned long ptr; unsigned long calc = 0; /* generate check for the bootloader to check on resume */ for (ptr = 0; ptr < 0x40000; ptr += 0x4) calc += __raw_readl(base+ptr); __raw_writel(calc, phys_to_virt(H1940_SUSPEND_CHECKSUM)); } if ( machine_is_aml_m5900() ) s3c2410_gpio_setpin(S3C2410_GPF(2), 1); if (machine_is_rx1950()) { /* According to S3C2442 user's manual, page 7-17, * when the system is operating in NAND boot mode, * the hardware pin configuration - EINT[23:21] – * must be set as input for starting up after * wakeup from sleep mode */ s3c_gpio_cfgpin(S3C2410_GPG(13), S3C2410_GPIO_INPUT); s3c_gpio_cfgpin(S3C2410_GPG(14), S3C2410_GPIO_INPUT); s3c_gpio_cfgpin(S3C2410_GPG(15), S3C2410_GPIO_INPUT); } }
static void s3c2410_pm_prepare(void) { /* ensure at least GSTATUS3 has the resume address */ { volatile unsigned long *ptr = phys_to_virt(0x30000900); *ptr = 0x55; } __raw_writel(0x7, S3C2410_GSTATUS2); S3C_PMDBG("GSTATUS2 0x%08x\n", __raw_readl(S3C2410_GSTATUS2)); __raw_writel(virt_to_phys(s3c_cpu_resume), S3C2410_GSTATUS3); S3C_PMDBG("GSTATUS3 0x%08x\n", __raw_readl(S3C2410_GSTATUS3)); S3C_PMDBG("GSTATUS4 0x%08x\n", __raw_readl(S3C2410_GSTATUS4)); if (machine_is_h1940()) { void *base = phys_to_virt(H1940_SUSPEND_CHECK); unsigned long ptr; unsigned long calc = 0; /* generate check for the bootloader to check on resume */ for (ptr = 0; ptr < 0x40000; ptr += 0x400) calc += __raw_readl(base+ptr); __raw_writel(calc, phys_to_virt(H1940_SUSPEND_CHECKSUM)); } /* the RX3715 uses similar code and the same H1940 and the * same offsets for resume and checksum pointers */ if (machine_is_rx3715()) { void *base = phys_to_virt(H1940_SUSPEND_CHECK); unsigned long ptr; unsigned long calc = 0; /* generate check for the bootloader to check on resume */ for (ptr = 0; ptr < 0x40000; ptr += 0x4) calc += __raw_readl(base+ptr); __raw_writel(calc, phys_to_virt(H1940_SUSPEND_CHECKSUM)); } if ( machine_is_aml_m5900() ) s3c2410_gpio_setpin(S3C2410_GPF(2), 1); }
static int __init h1940_init(void) { int ret; if (!machine_is_h1940()) return -ENODEV; /* configure some gpios */ ret = gpio_request(S3C_GPIO_END + 9, "speaker-power"); if (ret) goto err_out; ret = gpio_direction_output(S3C_GPIO_END + 9, 0); if (ret) goto err_gpio; s3c24xx_snd_device = platform_device_alloc("soc-audio", -1); if (!s3c24xx_snd_device) { ret = -ENOMEM; goto err_gpio; } platform_set_drvdata(s3c24xx_snd_device, &h1940_asoc); ret = platform_device_add(s3c24xx_snd_device); if (ret) goto err_plat; return 0; err_plat: platform_device_put(s3c24xx_snd_device); err_gpio: gpio_free(S3C_GPIO_END + 9); err_out: return ret; }
/* * Set up timer interrupt, and return the current time in seconds. * * Currently we only use timer4, as it is the only timer which has no * other function that can be exploited externally */ void __init s3c2410_init_time (void) { unsigned long tcon; unsigned long tcnt; unsigned long tcfg1; unsigned long tcfg0; gettimeoffset = s3c2410_gettimeoffset; tcnt = 0xffff; /* default value for tcnt */ /* read the current timer configuration bits */ tcon = __raw_readl(S3C2410_TCON); tcfg1 = __raw_readl(S3C2410_TCFG1); tcfg0 = __raw_readl(S3C2410_TCFG0); /* configure the system for whichever machine is in use */ if (machine_is_bast() || machine_is_vr1000()) { timer_ticks_usec = 12; /* timer is at 12MHz */ tcnt = (timer_ticks_usec * (1000*1000)) / HZ; } /* for the h1940, we use the pclk from the core to generate * the timer values. since 67.5MHz is not a value we can directly * generate the timer value from, we need to pre-scale and * divied before using it. * * overall divsior to get 200Hz is 337500 * we can fit tcnt if we pre-scale by 6, producing a tick rate * of 11.25MHz, and a tcnt of 56250. */ if (machine_is_h1940() || machine_is_smdk2410() ) { timer_ticks_usec = s3c2410_pclk / (1000*1000); timer_ticks_usec /= 6; tcfg1 &= ~S3C2410_TCFG1_MUX4_MASK; tcfg1 |= S3C2410_TCFG1_MUX4_DIV2; tcfg0 &= ~S3C2410_TCFG_PRESCALER1_MASK; tcfg0 |= ((6 - 1) / 2) << S3C2410_TCFG_PRESCALER1_SHIFT; tcnt = (s3c2410_pclk / 6) / HZ; } printk("setup_timer tcon=%08lx, tcnt %04lx, tcfg %08lx,%08lx\n", tcon, tcnt, tcfg0, tcfg1); /* check to see if timer is within 16bit range... */ if (tcnt > 0xffff) { panic("setup_timer: HZ is too small, cannot configure timer!"); return; } __raw_writel(tcfg1, S3C2410_TCFG1); __raw_writel(tcfg0, S3C2410_TCFG0); timer_startval = tcnt; __raw_writel(tcnt, S3C2410_TCNTB(4)); /* ensure timer is stopped... */ tcon &= ~(7<<20); tcon |= S3C2410_TCON_T4RELOAD; tcon |= S3C2410_TCON_T4MANUALUPD; __raw_writel(tcon, S3C2410_TCON); __raw_writel(tcnt, S3C2410_TCNTB(4)); __raw_writel(tcnt, S3C2410_TCMPB(4)); setup_irq(IRQ_TIMER4, &s3c2410_timer_irq); /* start the timer running */ tcon |= S3C2410_TCON_T4START; tcon &= ~S3C2410_TCON_T4MANUALUPD; __raw_writel(tcon, S3C2410_TCON); }