Merge branch 'samsung/dt' into next/dt
* samsung/dt: (27 commits) ARM: dts: Add intial dts file for EXYNOS4210 SoC, SMDKV310 and ORIGEN ARM: EXYNOS: Add Exynos4 device tree enabled board file rtc: rtc-s3c: Add device tree support input: samsung-keypad: Add device tree support ARM: S5PV210: Modify platform data for pl330 driver ARM: S5PC100: Modify platform data for pl330 driver ARM: S5P64x0: Modify platform data for pl330 driver ARM: EXYNOS: Add a alias for pdma clocks ARM: EXYNOS: Limit usage of pl330 device instance to non-dt build ARM: SAMSUNG: Add device tree support for pl330 dma engine wrappers DMA: PL330: Add device tree support ARM: EXYNOS: Modify platform data for pl330 driver DMA: PL330: Infer transfer direction from transfer request instead of platform data DMA: PL330: move filter function into driver serial: samsung: Fix build for non-Exynos4210 devices serial: samsung: add device tree support serial: samsung: merge probe() function from all SoC specific extensions serial: samsung: merge all SoC specific port reset functions ARM: SAMSUNG: register uart clocks to clock lookup list serial: samsung: remove all uses of get_clksrc and set_clksrc ...
This commit is contained in:
Коммит
31b2a86845
|
@ -0,0 +1,8 @@
|
|||
* Insignal's Exynos4210 based Origen evaluation board
|
||||
|
||||
Origen low-cost evaluation board is based on Samsung's Exynos4210 SoC.
|
||||
|
||||
Required root node properties:
|
||||
- compatible = should be one or more of the following.
|
||||
(a) "samsung,smdkv310" - for Samsung's SMDKV310 eval board.
|
||||
(b) "samsung,exynos4210" - for boards based on Exynos4210 SoC.
|
|
@ -0,0 +1,8 @@
|
|||
* Samsung's Exynos4210 based SMDKV310 evaluation board
|
||||
|
||||
SMDKV310 evaluation board is based on Samsung's Exynos4210 SoC.
|
||||
|
||||
Required root node properties:
|
||||
- compatible = should be one or more of the following.
|
||||
(a) "samsung,smdkv310" - for Samsung's SMDKV310 eval board.
|
||||
(b) "samsung,exynos4210" - for boards based on Exynos4210 SoC.
|
|
@ -0,0 +1,30 @@
|
|||
* ARM PrimeCell PL330 DMA Controller
|
||||
|
||||
The ARM PrimeCell PL330 DMA controller can move blocks of memory contents
|
||||
between memory and peripherals or memory to memory.
|
||||
|
||||
Required properties:
|
||||
- compatible: should include both "arm,pl330" and "arm,primecell".
|
||||
- reg: physical base address of the controller and length of memory mapped
|
||||
region.
|
||||
- interrupts: interrupt number to the cpu.
|
||||
|
||||
Example:
|
||||
|
||||
pdma0: pdma@12680000 {
|
||||
compatible = "arm,pl330", "arm,primecell";
|
||||
reg = <0x12680000 0x1000>;
|
||||
interrupts = <99>;
|
||||
};
|
||||
|
||||
Client drivers (device nodes requiring dma transfers from dev-to-mem or
|
||||
mem-to-dev) should specify the DMA channel numbers using a two-value pair
|
||||
as shown below.
|
||||
|
||||
[property name] = <[phandle of the dma controller] [dma request id]>;
|
||||
|
||||
where 'dma request id' is the dma request number which is connected
|
||||
to the client controller. The 'property name' is recommended to be
|
||||
of the form <name>-dma-channel.
|
||||
|
||||
Example: tx-dma-channel = <&pdma0 12>;
|
|
@ -0,0 +1,40 @@
|
|||
Samsung Exynos4 GPIO Controller
|
||||
|
||||
Required properties:
|
||||
- compatible: Compatible property value should be "samsung,exynos4-gpio>".
|
||||
|
||||
- reg: Physical base address of the controller and length of memory mapped
|
||||
region.
|
||||
|
||||
- #gpio-cells: Should be 4. The syntax of the gpio specifier used by client nodes
|
||||
should be the following with values derived from the SoC user manual.
|
||||
<[phandle of the gpio controller node]
|
||||
[pin number within the gpio controller]
|
||||
[mux function]
|
||||
[pull up/down]
|
||||
[drive strength]>
|
||||
|
||||
Values for gpio specifier:
|
||||
- Pin number: is a value between 0 to 7.
|
||||
- Pull Up/Down: 0 - Pull Up/Down Disabled.
|
||||
1 - Pull Down Enabled.
|
||||
3 - Pull Up Enabled.
|
||||
- Drive Strength: 0 - 1x,
|
||||
1 - 3x,
|
||||
2 - 2x,
|
||||
3 - 4x
|
||||
|
||||
- gpio-controller: Specifies that the node is a gpio controller.
|
||||
- #address-cells: should be 1.
|
||||
- #size-cells: should be 1.
|
||||
|
||||
Example:
|
||||
|
||||
gpa0: gpio-controller@11400000 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400000 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
gpio-controller;
|
||||
};
|
|
@ -0,0 +1,88 @@
|
|||
* Samsung's Keypad Controller device tree bindings
|
||||
|
||||
Samsung's Keypad controller is used to interface a SoC with a matrix-type
|
||||
keypad device. The keypad controller supports multiple row and column lines.
|
||||
A key can be placed at each intersection of a unique row and a unique column.
|
||||
The keypad controller can sense a key-press and key-release and report the
|
||||
event using a interrupt to the cpu.
|
||||
|
||||
Required SoC Specific Properties:
|
||||
- compatible: should be one of the following
|
||||
- "samsung,s3c6410-keypad": For controllers compatible with s3c6410 keypad
|
||||
controller.
|
||||
- "samsung,s5pv210-keypad": For controllers compatible with s5pv210 keypad
|
||||
controller.
|
||||
|
||||
- reg: physical base address of the controller and length of memory mapped
|
||||
region.
|
||||
|
||||
- interrupts: The interrupt number to the cpu.
|
||||
|
||||
Required Board Specific Properties:
|
||||
- samsung,keypad-num-rows: Number of row lines connected to the keypad
|
||||
controller.
|
||||
|
||||
- samsung,keypad-num-columns: Number of column lines connected to the
|
||||
keypad controller.
|
||||
|
||||
- row-gpios: List of gpios used as row lines. The gpio specifier for
|
||||
this property depends on the gpio controller to which these row lines
|
||||
are connected.
|
||||
|
||||
- col-gpios: List of gpios used as column lines. The gpio specifier for
|
||||
this property depends on the gpio controller to which these column
|
||||
lines are connected.
|
||||
|
||||
- Keys represented as child nodes: Each key connected to the keypad
|
||||
controller is represented as a child node to the keypad controller
|
||||
device node and should include the following properties.
|
||||
- keypad,row: the row number to which the key is connected.
|
||||
- keypad,column: the column number to which the key is connected.
|
||||
- linux,code: the key-code to be reported when the key is pressed
|
||||
and released.
|
||||
|
||||
Optional Properties specific to linux:
|
||||
- linux,keypad-no-autorepeat: do no enable autorepeat feature.
|
||||
- linux,keypad-wakeup: use any event on keypad as wakeup event.
|
||||
|
||||
|
||||
Example:
|
||||
keypad@100A0000 {
|
||||
compatible = "samsung,s5pv210-keypad";
|
||||
reg = <0x100A0000 0x100>;
|
||||
interrupts = <173>;
|
||||
samsung,keypad-num-rows = <2>;
|
||||
samsung,keypad-num-columns = <8>;
|
||||
linux,input-no-autorepeat;
|
||||
linux,input-wakeup;
|
||||
|
||||
row-gpios = <&gpx2 0 3 3 0
|
||||
&gpx2 1 3 3 0>;
|
||||
|
||||
col-gpios = <&gpx1 0 3 0 0
|
||||
&gpx1 1 3 0 0
|
||||
&gpx1 2 3 0 0
|
||||
&gpx1 3 3 0 0
|
||||
&gpx1 4 3 0 0
|
||||
&gpx1 5 3 0 0
|
||||
&gpx1 6 3 0 0
|
||||
&gpx1 7 3 0 0>;
|
||||
|
||||
key_1 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <3>;
|
||||
linux,code = <2>;
|
||||
};
|
||||
|
||||
key_2 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <4>;
|
||||
linux,code = <3>;
|
||||
};
|
||||
|
||||
key_3 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <5>;
|
||||
linux,code = <4>;
|
||||
};
|
||||
};
|
|
@ -0,0 +1,20 @@
|
|||
* Samsung's S3C Real Time Clock controller
|
||||
|
||||
Required properties:
|
||||
- compatible: should be one of the following.
|
||||
* "samsung,s3c2410-rtc" - for controllers compatible with s3c2410 rtc.
|
||||
* "samsung,s3c6410-rtc" - for controllers compatible with s3c6410 rtc.
|
||||
- reg: physical base address of the controller and length of memory mapped
|
||||
region.
|
||||
- interrupts: Two interrupt numbers to the cpu should be specified. First
|
||||
interrupt number is the rtc alarm interupt and second interrupt number
|
||||
is the rtc tick interrupt. The number of cells representing a interrupt
|
||||
depends on the parent interrupt controller.
|
||||
|
||||
Example:
|
||||
|
||||
rtc@10070000 {
|
||||
compatible = "samsung,s3c6410-rtc";
|
||||
reg = <0x10070000 0x100>;
|
||||
interrupts = <44 0 45 0>;
|
||||
};
|
|
@ -0,0 +1,14 @@
|
|||
* Samsung's UART Controller
|
||||
|
||||
The Samsung's UART controller is used for interfacing SoC with serial communicaion
|
||||
devices.
|
||||
|
||||
Required properties:
|
||||
- compatible: should be
|
||||
- "samsung,exynos4210-uart", for UART's compatible with Exynos4210 uart ports.
|
||||
|
||||
- reg: base physical address of the controller and length of memory mapped
|
||||
region.
|
||||
|
||||
- interrupts: interrupt number to the cpu. The interrupt specifier format depends
|
||||
on the interrupt controller parent.
|
|
@ -0,0 +1,137 @@
|
|||
/*
|
||||
* Samsung's Exynos4210 based Origen board device tree source
|
||||
*
|
||||
* Copyright (c) 2010-2011 Samsung Electronics Co., Ltd.
|
||||
* http://www.samsung.com
|
||||
* Copyright (c) 2010-2011 Linaro Ltd.
|
||||
* www.linaro.org
|
||||
*
|
||||
* Device tree source file for Insignal's Origen board which is based on
|
||||
* Samsung's Exynos4210 SoC.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
/dts-v1/;
|
||||
/include/ "exynos4210.dtsi"
|
||||
|
||||
/ {
|
||||
model = "Insignal Origen evaluation board based on Exynos4210";
|
||||
compatible = "insignal,origen", "samsung,exynos4210";
|
||||
|
||||
memory {
|
||||
reg = <0x40000000 0x40000000>;
|
||||
};
|
||||
|
||||
chosen {
|
||||
bootargs ="root=/dev/ram0 rw ramdisk=8192 initrd=0x41000000,8M console=ttySAC2,115200 init=/linuxrc";
|
||||
};
|
||||
|
||||
sdhci@12530000 {
|
||||
samsung,sdhci-bus-width = <4>;
|
||||
linux,mmc_cap_4_bit_data;
|
||||
samsung,sdhci-cd-internal;
|
||||
gpio-cd = <&gpk2 2 2 3 3>;
|
||||
gpios = <&gpk2 0 2 0 3>,
|
||||
<&gpk2 1 2 0 3>,
|
||||
<&gpk2 3 2 3 3>,
|
||||
<&gpk2 4 2 3 3>,
|
||||
<&gpk2 5 2 3 3>,
|
||||
<&gpk2 6 2 3 3>;
|
||||
};
|
||||
|
||||
sdhci@12510000 {
|
||||
samsung,sdhci-bus-width = <4>;
|
||||
linux,mmc_cap_4_bit_data;
|
||||
samsung,sdhci-cd-internal;
|
||||
gpio-cd = <&gpk0 2 2 3 3>;
|
||||
gpios = <&gpk0 0 2 0 3>,
|
||||
<&gpk0 1 2 0 3>,
|
||||
<&gpk0 3 2 3 3>,
|
||||
<&gpk0 4 2 3 3>,
|
||||
<&gpk0 5 2 3 3>,
|
||||
<&gpk0 6 2 3 3>;
|
||||
};
|
||||
|
||||
gpio_keys {
|
||||
compatible = "gpio-keys";
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
|
||||
up {
|
||||
label = "Up";
|
||||
gpios = <&gpx2 0 0 0 2>;
|
||||
linux,code = <103>;
|
||||
};
|
||||
|
||||
down {
|
||||
label = "Down";
|
||||
gpios = <&gpx2 1 0 0 2>;
|
||||
linux,code = <108>;
|
||||
};
|
||||
|
||||
back {
|
||||
label = "Back";
|
||||
gpios = <&gpx1 7 0 0 2>;
|
||||
linux,code = <158>;
|
||||
};
|
||||
|
||||
home {
|
||||
label = "Home";
|
||||
gpios = <&gpx1 6 0 0 2>;
|
||||
linux,code = <102>;
|
||||
};
|
||||
|
||||
menu {
|
||||
label = "Menu";
|
||||
gpios = <&gpx1 5 0 0 2>;
|
||||
linux,code = <139>;
|
||||
};
|
||||
};
|
||||
|
||||
keypad@100A0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
sdhci@12520000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
sdhci@12540000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13860000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13870000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13880000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13890000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138A0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138B0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138C0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138D0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
};
|
|
@ -0,0 +1,182 @@
|
|||
/*
|
||||
* Samsung's Exynos4210 based SMDKV310 board device tree source
|
||||
*
|
||||
* Copyright (c) 2010-2011 Samsung Electronics Co., Ltd.
|
||||
* http://www.samsung.com
|
||||
* Copyright (c) 2010-2011 Linaro Ltd.
|
||||
* www.linaro.org
|
||||
*
|
||||
* Device tree source file for Samsung's SMDKV310 board which is based on
|
||||
* Samsung's Exynos4210 SoC.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
/dts-v1/;
|
||||
/include/ "exynos4210.dtsi"
|
||||
|
||||
/ {
|
||||
model = "Samsung smdkv310 evaluation board based on Exynos4210";
|
||||
compatible = "samsung,smdkv310", "samsung,exynos4210";
|
||||
|
||||
memory {
|
||||
reg = <0x40000000 0x80000000>;
|
||||
};
|
||||
|
||||
chosen {
|
||||
bootargs = "root=/dev/ram0 rw ramdisk=8192 initrd=0x41000000,8M console=ttySAC1,115200 init=/linuxrc";
|
||||
};
|
||||
|
||||
sdhci@12530000 {
|
||||
samsung,sdhci-bus-width = <4>;
|
||||
linux,mmc_cap_4_bit_data;
|
||||
samsung,sdhci-cd-internal;
|
||||
gpio-cd = <&gpk2 2 2 3 3>;
|
||||
gpios = <&gpk2 0 2 0 3>,
|
||||
<&gpk2 1 2 0 3>,
|
||||
<&gpk2 3 2 3 3>,
|
||||
<&gpk2 4 2 3 3>,
|
||||
<&gpk2 5 2 3 3>,
|
||||
<&gpk2 6 2 3 3>;
|
||||
};
|
||||
|
||||
keypad@100A0000 {
|
||||
samsung,keypad-num-rows = <2>;
|
||||
samsung,keypad-num-columns = <8>;
|
||||
linux,keypad-no-autorepeat;
|
||||
linux,keypad-wakeup;
|
||||
|
||||
row-gpios = <&gpx2 0 3 3 0>,
|
||||
<&gpx2 1 3 3 0>;
|
||||
|
||||
col-gpios = <&gpx1 0 3 0 0>,
|
||||
<&gpx1 1 3 0 0>,
|
||||
<&gpx1 2 3 0 0>,
|
||||
<&gpx1 3 3 0 0>,
|
||||
<&gpx1 4 3 0 0>,
|
||||
<&gpx1 5 3 0 0>,
|
||||
<&gpx1 6 3 0 0>,
|
||||
<&gpx1 7 3 0 0>;
|
||||
|
||||
key_1 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <3>;
|
||||
linux,code = <2>;
|
||||
};
|
||||
|
||||
key_2 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <4>;
|
||||
linux,code = <3>;
|
||||
};
|
||||
|
||||
key_3 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <5>;
|
||||
linux,code = <4>;
|
||||
};
|
||||
|
||||
key_4 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <6>;
|
||||
linux,code = <5>;
|
||||
};
|
||||
|
||||
key_5 {
|
||||
keypad,row = <0>;
|
||||
keypad,column = <7>;
|
||||
linux,code = <6>;
|
||||
};
|
||||
|
||||
key_a {
|
||||
keypad,row = <1>;
|
||||
keypad,column = <3>;
|
||||
linux,code = <30>;
|
||||
};
|
||||
|
||||
key_b {
|
||||
keypad,row = <1>;
|
||||
keypad,column = <4>;
|
||||
linux,code = <48>;
|
||||
};
|
||||
|
||||
key_c {
|
||||
keypad,row = <1>;
|
||||
keypad,column = <5>;
|
||||
linux,code = <46>;
|
||||
};
|
||||
|
||||
key_d {
|
||||
keypad,row = <1>;
|
||||
keypad,column = <6>;
|
||||
linux,code = <32>;
|
||||
};
|
||||
|
||||
key_e {
|
||||
keypad,row = <1>;
|
||||
keypad,column = <7>;
|
||||
linux,code = <18>;
|
||||
};
|
||||
};
|
||||
|
||||
i2c@13860000 {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <0>;
|
||||
samsung,i2c-sda-delay = <100>;
|
||||
samsung,i2c-max-bus-freq = <20000>;
|
||||
gpios = <&gpd1 0 2 3 0>,
|
||||
<&gpd1 1 2 3 0>;
|
||||
|
||||
eeprom@50 {
|
||||
compatible = "samsung,24ad0xd1";
|
||||
reg = <0x50>;
|
||||
};
|
||||
|
||||
eeprom@52 {
|
||||
compatible = "samsung,24ad0xd1";
|
||||
reg = <0x52>;
|
||||
};
|
||||
};
|
||||
|
||||
sdhci@12510000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
sdhci@12520000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
sdhci@12540000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13870000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13880000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@13890000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138A0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138B0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138C0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
|
||||
i2c@138D0000 {
|
||||
status = "disabled";
|
||||
};
|
||||
};
|
|
@ -0,0 +1,397 @@
|
|||
/*
|
||||
* Samsung's Exynos4210 SoC device tree source
|
||||
*
|
||||
* Copyright (c) 2010-2011 Samsung Electronics Co., Ltd.
|
||||
* http://www.samsung.com
|
||||
* Copyright (c) 2010-2011 Linaro Ltd.
|
||||
* www.linaro.org
|
||||
*
|
||||
* Samsung's Exynos4210 SoC device nodes are listed in this file. Exynos4210
|
||||
* based board files can include this file and provide values for board specfic
|
||||
* bindings.
|
||||
*
|
||||
* Note: This file does not include device nodes for all the controllers in
|
||||
* Exynos4210 SoC. As device tree coverage for Exynos4210 increases, additional
|
||||
* nodes can be added to this file.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
/include/ "skeleton.dtsi"
|
||||
|
||||
/ {
|
||||
compatible = "samsung,exynos4210";
|
||||
interrupt-parent = <&gic>;
|
||||
|
||||
gic:interrupt-controller@10490000 {
|
||||
compatible = "arm,cortex-a9-gic";
|
||||
#interrupt-cells = <3>;
|
||||
interrupt-controller;
|
||||
reg = <0x10490000 0x1000>, <0x10480000 0x100>;
|
||||
};
|
||||
|
||||
watchdog@10060000 {
|
||||
compatible = "samsung,s3c2410-wdt";
|
||||
reg = <0x10060000 0x100>;
|
||||
interrupts = <0 43 0>;
|
||||
};
|
||||
|
||||
rtc@10070000 {
|
||||
compatible = "samsung,s3c6410-rtc";
|
||||
reg = <0x10070000 0x100>;
|
||||
interrupts = <0 44 0>, <0 45 0>;
|
||||
};
|
||||
|
||||
keypad@100A0000 {
|
||||
compatible = "samsung,s5pv210-keypad";
|
||||
reg = <0x100A0000 0x100>;
|
||||
interrupts = <0 109 0>;
|
||||
};
|
||||
|
||||
sdhci@12510000 {
|
||||
compatible = "samsung,exynos4210-sdhci";
|
||||
reg = <0x12510000 0x100>;
|
||||
interrupts = <0 73 0>;
|
||||
};
|
||||
|
||||
sdhci@12520000 {
|
||||
compatible = "samsung,exynos4210-sdhci";
|
||||
reg = <0x12520000 0x100>;
|
||||
interrupts = <0 74 0>;
|
||||
};
|
||||
|
||||
sdhci@12530000 {
|
||||
compatible = "samsung,exynos4210-sdhci";
|
||||
reg = <0x12530000 0x100>;
|
||||
interrupts = <0 75 0>;
|
||||
};
|
||||
|
||||
sdhci@12540000 {
|
||||
compatible = "samsung,exynos4210-sdhci";
|
||||
reg = <0x12540000 0x100>;
|
||||
interrupts = <0 76 0>;
|
||||
};
|
||||
|
||||
serial@13800000 {
|
||||
compatible = "samsung,exynos4210-uart";
|
||||
reg = <0x13800000 0x100>;
|
||||
interrupts = <0 52 0>;
|
||||
};
|
||||
|
||||
serial@13810000 {
|
||||
compatible = "samsung,exynos4210-uart";
|
||||
reg = <0x13810000 0x100>;
|
||||
interrupts = <0 53 0>;
|
||||
};
|
||||
|
||||
serial@13820000 {
|
||||
compatible = "samsung,exynos4210-uart";
|
||||
reg = <0x13820000 0x100>;
|
||||
interrupts = <0 54 0>;
|
||||
};
|
||||
|
||||
serial@13830000 {
|
||||
compatible = "samsung,exynos4210-uart";
|
||||
reg = <0x13830000 0x100>;
|
||||
interrupts = <0 55 0>;
|
||||
};
|
||||
|
||||
i2c@13860000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x13860000 0x100>;
|
||||
interrupts = <0 58 0>;
|
||||
};
|
||||
|
||||
i2c@13870000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x13870000 0x100>;
|
||||
interrupts = <0 59 0>;
|
||||
};
|
||||
|
||||
i2c@13880000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x13880000 0x100>;
|
||||
interrupts = <0 60 0>;
|
||||
};
|
||||
|
||||
i2c@13890000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x13890000 0x100>;
|
||||
interrupts = <0 61 0>;
|
||||
};
|
||||
|
||||
i2c@138A0000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x138A0000 0x100>;
|
||||
interrupts = <0 62 0>;
|
||||
};
|
||||
|
||||
i2c@138B0000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x138B0000 0x100>;
|
||||
interrupts = <0 63 0>;
|
||||
};
|
||||
|
||||
i2c@138C0000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x138C0000 0x100>;
|
||||
interrupts = <0 64 0>;
|
||||
};
|
||||
|
||||
i2c@138D0000 {
|
||||
compatible = "samsung,s3c2440-i2c";
|
||||
reg = <0x138D0000 0x100>;
|
||||
interrupts = <0 65 0>;
|
||||
};
|
||||
|
||||
amba {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
compatible = "arm,amba-bus";
|
||||
interrupt-parent = <&gic>;
|
||||
ranges;
|
||||
|
||||
pdma0: pdma@12680000 {
|
||||
compatible = "arm,pl330", "arm,primecell";
|
||||
reg = <0x12680000 0x1000>;
|
||||
interrupts = <0 35 0>;
|
||||
};
|
||||
|
||||
pdma1: pdma@12690000 {
|
||||
compatible = "arm,pl330", "arm,primecell";
|
||||
reg = <0x12690000 0x1000>;
|
||||
interrupts = <0 36 0>;
|
||||
};
|
||||
};
|
||||
|
||||
gpio-controllers {
|
||||
#address-cells = <1>;
|
||||
#size-cells = <1>;
|
||||
gpio-controller;
|
||||
ranges;
|
||||
|
||||
gpa0: gpio-controller@11400000 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400000 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpa1: gpio-controller@11400020 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400020 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpb: gpio-controller@11400040 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400040 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpc0: gpio-controller@11400060 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400060 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpc1: gpio-controller@11400080 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400080 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpd0: gpio-controller@114000A0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x114000A0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpd1: gpio-controller@114000C0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x114000C0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpe0: gpio-controller@114000E0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x114000E0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpe1: gpio-controller@11400100 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400100 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpe2: gpio-controller@11400120 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400120 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpe3: gpio-controller@11400140 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400140 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpe4: gpio-controller@11400160 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400160 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpf0: gpio-controller@11400180 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11400180 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpf1: gpio-controller@114001A0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x114001A0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpf2: gpio-controller@114001C0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x114001C0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpf3: gpio-controller@114001E0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x114001E0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpj0: gpio-controller@11000000 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000000 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpj1: gpio-controller@11000020 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000020 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpk0: gpio-controller@11000040 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000040 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpk1: gpio-controller@11000060 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000060 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpk2: gpio-controller@11000080 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000080 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpk3: gpio-controller@110000A0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x110000A0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpl0: gpio-controller@110000C0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x110000C0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpl1: gpio-controller@110000E0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x110000E0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpl2: gpio-controller@11000100 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000100 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy0: gpio-controller@11000120 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000120 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy1: gpio-controller@11000140 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000140 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy2: gpio-controller@11000160 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000160 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy3: gpio-controller@11000180 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000180 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy4: gpio-controller@110001A0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x110001A0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy5: gpio-controller@110001C0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x110001C0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpy6: gpio-controller@110001E0 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x110001E0 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpx0: gpio-controller@11000C00 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000C00 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpx1: gpio-controller@11000C20 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000C20 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpx2: gpio-controller@11000C40 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000C40 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpx3: gpio-controller@11000C60 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x11000C60 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
|
||||
gpz: gpio-controller@03860000 {
|
||||
compatible = "samsung,exynos4-gpio";
|
||||
reg = <0x03860000 0x20>;
|
||||
#gpio-cells = <4>;
|
||||
};
|
||||
};
|
||||
};
|
|
@ -57,6 +57,11 @@ config EXYNOS4_MCT
|
|||
help
|
||||
Use MCT (Multi Core Timer) as kernel timers
|
||||
|
||||
config EXYNOS4_DEV_DMA
|
||||
bool
|
||||
help
|
||||
Compile in amba device definitions for DMA controller
|
||||
|
||||
config EXYNOS4_DEV_AHCI
|
||||
bool
|
||||
help
|
||||
|
@ -177,6 +182,7 @@ config MACH_SMDKV310
|
|||
select SAMSUNG_DEV_BACKLIGHT
|
||||
select EXYNOS4_DEV_AHCI
|
||||
select SAMSUNG_DEV_KEYPAD
|
||||
select EXYNOS4_DEV_DMA
|
||||
select EXYNOS4_DEV_PD
|
||||
select SAMSUNG_DEV_PWM
|
||||
select EXYNOS4_DEV_SYSMMU
|
||||
|
@ -197,6 +203,7 @@ config MACH_ARMLEX4210
|
|||
select S3C_DEV_HSMMC2
|
||||
select S3C_DEV_HSMMC3
|
||||
select EXYNOS4_DEV_AHCI
|
||||
select EXYNOS4_DEV_DMA
|
||||
select EXYNOS4_DEV_SYSMMU
|
||||
select EXYNOS4_SETUP_SDHCI
|
||||
help
|
||||
|
@ -222,6 +229,7 @@ config MACH_UNIVERSAL_C210
|
|||
select S5P_DEV_MFC
|
||||
select S5P_DEV_ONENAND
|
||||
select S5P_DEV_TV
|
||||
select EXYNOS4_DEV_DMA
|
||||
select EXYNOS4_DEV_PD
|
||||
select EXYNOS4_SETUP_FIMD0
|
||||
select EXYNOS4_SETUP_I2C1
|
||||
|
@ -255,6 +263,7 @@ config MACH_NURI
|
|||
select S5P_DEV_MFC
|
||||
select S5P_DEV_USB_EHCI
|
||||
select S5P_SETUP_MIPIPHY
|
||||
select EXYNOS4_DEV_DMA
|
||||
select EXYNOS4_DEV_PD
|
||||
select EXYNOS4_SETUP_FIMC
|
||||
select EXYNOS4_SETUP_FIMD0
|
||||
|
@ -287,6 +296,7 @@ config MACH_ORIGEN
|
|||
select S5P_DEV_USB_EHCI
|
||||
select SAMSUNG_DEV_BACKLIGHT
|
||||
select SAMSUNG_DEV_PWM
|
||||
select EXYNOS4_DEV_DMA
|
||||
select EXYNOS4_DEV_PD
|
||||
select EXYNOS4_SETUP_FIMD0
|
||||
select EXYNOS4_SETUP_SDHCI
|
||||
|
@ -327,6 +337,20 @@ config MACH_SMDK4412
|
|||
Machine support for Samsung SMDK4412
|
||||
endif
|
||||
|
||||
comment "Flattened Device Tree based board for Exynos4 based SoC"
|
||||
|
||||
config MACH_EXYNOS4_DT
|
||||
bool "Samsung Exynos4 Machine using device tree"
|
||||
select CPU_EXYNOS4210
|
||||
select USE_OF
|
||||
select ARM_AMBA
|
||||
select HAVE_SAMSUNG_KEYPAD if INPUT_KEYBOARD
|
||||
help
|
||||
Machine support for Samsung Exynos4 machine with device tree enabled.
|
||||
Select this if a fdt blob is available for the Exynos4 SoC based board.
|
||||
Note: This is under development and not all peripherals can be supported
|
||||
with this machine file.
|
||||
|
||||
if ARCH_EXYNOS4
|
||||
|
||||
comment "Configuration for HSMMC 8-bit bus width"
|
||||
|
|
|
@ -13,7 +13,7 @@ obj- :=
|
|||
# Core support for EXYNOS4 system
|
||||
|
||||
obj-$(CONFIG_ARCH_EXYNOS4) += cpu.o init.o clock.o irq-combiner.o setup-i2c0.o
|
||||
obj-$(CONFIG_ARCH_EXYNOS4) += irq-eint.o dma.o pmu.o
|
||||
obj-$(CONFIG_ARCH_EXYNOS4) += irq-eint.o pmu.o
|
||||
obj-$(CONFIG_CPU_EXYNOS4210) += clock-exynos4210.o
|
||||
obj-$(CONFIG_SOC_EXYNOS4212) += clock-exynos4212.o
|
||||
obj-$(CONFIG_PM) += pm.o
|
||||
|
@ -37,6 +37,8 @@ obj-$(CONFIG_MACH_ORIGEN) += mach-origen.o
|
|||
obj-$(CONFIG_MACH_SMDK4212) += mach-smdk4x12.o
|
||||
obj-$(CONFIG_MACH_SMDK4412) += mach-smdk4x12.o
|
||||
|
||||
obj-$(CONFIG_MACH_EXYNOS4_DT) += mach-exynos4-dt.o
|
||||
|
||||
# device support
|
||||
|
||||
obj-$(CONFIG_ARCH_EXYNOS4) += dev-audio.o
|
||||
|
@ -44,6 +46,7 @@ obj-$(CONFIG_EXYNOS4_DEV_AHCI) += dev-ahci.o
|
|||
obj-$(CONFIG_EXYNOS4_DEV_PD) += dev-pd.o
|
||||
obj-$(CONFIG_EXYNOS4_DEV_SYSMMU) += dev-sysmmu.o
|
||||
obj-$(CONFIG_EXYNOS4_DEV_DWMCI) += dev-dwmci.o
|
||||
obj-$(CONFIG_EXYNOS4_DEV_DMA) += dma.o
|
||||
|
||||
obj-$(CONFIG_EXYNOS4_SETUP_FIMC) += setup-fimc.o
|
||||
obj-$(CONFIG_EXYNOS4_SETUP_FIMD0) += setup-fimd0.o
|
||||
|
|
|
@ -552,16 +552,6 @@ static struct clk init_clocks_off[] = {
|
|||
.devname = "s5p-sdo",
|
||||
.enable = exynos4_clk_dac_ctrl,
|
||||
.ctrlbit = (1 << 0),
|
||||
}, {
|
||||
.name = "dma",
|
||||
.devname = "dma-pl330.0",
|
||||
.enable = exynos4_clk_ip_fsys_ctrl,
|
||||
.ctrlbit = (1 << 0),
|
||||
}, {
|
||||
.name = "dma",
|
||||
.devname = "dma-pl330.1",
|
||||
.enable = exynos4_clk_ip_fsys_ctrl,
|
||||
.ctrlbit = (1 << 1),
|
||||
}, {
|
||||
.name = "adc",
|
||||
.enable = exynos4_clk_ip_peril_ctrl,
|
||||
|
@ -778,6 +768,20 @@ static struct clk init_clocks[] = {
|
|||
}
|
||||
};
|
||||
|
||||
static struct clk clk_pdma0 = {
|
||||
.name = "dma",
|
||||
.devname = "dma-pl330.0",
|
||||
.enable = exynos4_clk_ip_fsys_ctrl,
|
||||
.ctrlbit = (1 << 0),
|
||||
};
|
||||
|
||||
static struct clk clk_pdma1 = {
|
||||
.name = "dma",
|
||||
.devname = "dma-pl330.1",
|
||||
.enable = exynos4_clk_ip_fsys_ctrl,
|
||||
.ctrlbit = (1 << 1),
|
||||
};
|
||||
|
||||
struct clk *clkset_group_list[] = {
|
||||
[0] = &clk_ext_xtal_mux,
|
||||
[1] = &clk_xusbxti,
|
||||
|
@ -1009,46 +1013,6 @@ static struct clksrc_clk clk_dout_mmc4 = {
|
|||
|
||||
static struct clksrc_clk clksrcs[] = {
|
||||
{
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.0",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 0),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 0, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 0, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.1",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 4),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 4, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 4, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.2",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 8),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 8, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 8, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.3",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 12),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 12, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 12, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "sclk_pwm",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
|
@ -1237,6 +1201,54 @@ static struct clksrc_clk clksrcs[] = {
|
|||
}
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart0 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "exynos4210-uart.0",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 0),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 0, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 0, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart1 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "exynos4210-uart.1",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 4),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 4, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 4, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart2 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "exynos4210-uart.2",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 8),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 8, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 8, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart3 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "exynos4210-uart.3",
|
||||
.enable = exynos4_clksrc_mask_peril0_ctrl,
|
||||
.ctrlbit = (1 << 12),
|
||||
},
|
||||
.sources = &clkset_group,
|
||||
.reg_src = { .reg = S5P_CLKSRC_PERIL0, .shift = 12, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLKDIV_PERIL0, .shift = 12, .size = 4 },
|
||||
};
|
||||
|
||||
/* Clock initialization code */
|
||||
static struct clksrc_clk *sysclks[] = {
|
||||
&clk_mout_apll,
|
||||
|
@ -1271,6 +1283,27 @@ static struct clksrc_clk *sysclks[] = {
|
|||
&clk_mout_mfc1,
|
||||
};
|
||||
|
||||
static struct clk *clk_cdev[] = {
|
||||
&clk_pdma0,
|
||||
&clk_pdma1,
|
||||
};
|
||||
|
||||
static struct clksrc_clk *clksrc_cdev[] = {
|
||||
&clk_sclk_uart0,
|
||||
&clk_sclk_uart1,
|
||||
&clk_sclk_uart2,
|
||||
&clk_sclk_uart3,
|
||||
};
|
||||
|
||||
static struct clk_lookup exynos4_clk_lookup[] = {
|
||||
CLKDEV_INIT("exynos4210-uart.0", "clk_uart_baud0", &clk_sclk_uart0.clk),
|
||||
CLKDEV_INIT("exynos4210-uart.1", "clk_uart_baud0", &clk_sclk_uart1.clk),
|
||||
CLKDEV_INIT("exynos4210-uart.2", "clk_uart_baud0", &clk_sclk_uart2.clk),
|
||||
CLKDEV_INIT("exynos4210-uart.3", "clk_uart_baud0", &clk_sclk_uart3.clk),
|
||||
CLKDEV_INIT("dma-pl330.0", "apb_pclk", &clk_pdma0),
|
||||
CLKDEV_INIT("dma-pl330.1", "apb_pclk", &clk_pdma1),
|
||||
};
|
||||
|
||||
static int xtal_rate;
|
||||
|
||||
static unsigned long exynos4_fout_apll_get_rate(struct clk *clk)
|
||||
|
@ -1478,11 +1511,19 @@ void __init exynos4_register_clocks(void)
|
|||
for (ptr = 0; ptr < ARRAY_SIZE(sclk_tv); ptr++)
|
||||
s3c_register_clksrc(sclk_tv[ptr], 1);
|
||||
|
||||
for (ptr = 0; ptr < ARRAY_SIZE(clksrc_cdev); ptr++)
|
||||
s3c_register_clksrc(clksrc_cdev[ptr], 1);
|
||||
|
||||
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
|
||||
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
|
||||
|
||||
s3c24xx_register_clocks(clk_cdev, ARRAY_SIZE(clk_cdev));
|
||||
for (ptr = 0; ptr < ARRAY_SIZE(clk_cdev); ptr++)
|
||||
s3c_disable_clocks(clk_cdev[ptr], 1);
|
||||
|
||||
s3c_register_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
s3c_disable_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
clkdev_add_table(exynos4_clk_lookup, ARRAY_SIZE(exynos4_clk_lookup));
|
||||
|
||||
register_syscore_ops(&exynos4_clock_syscore_ops);
|
||||
s3c24xx_register_clock(&dummy_apb_pclk);
|
||||
|
|
|
@ -10,6 +10,8 @@
|
|||
|
||||
#include <linux/sched.h>
|
||||
#include <linux/sysdev.h>
|
||||
#include <linux/of.h>
|
||||
#include <linux/of_irq.h>
|
||||
|
||||
#include <asm/mach/map.h>
|
||||
#include <asm/mach/irq.h>
|
||||
|
@ -218,13 +220,26 @@ static void exynos4_gic_irq_fix_base(struct irq_data *d)
|
|||
(gic_bank_offset * smp_processor_id());
|
||||
}
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static const struct of_device_id exynos4_dt_irq_match[] = {
|
||||
{ .compatible = "arm,cortex-a9-gic", .data = gic_of_init, },
|
||||
{},
|
||||
};
|
||||
#endif
|
||||
|
||||
void __init exynos4_init_irq(void)
|
||||
{
|
||||
int irq;
|
||||
|
||||
gic_bank_offset = soc_is_exynos4412() ? 0x4000 : 0x8000;
|
||||
|
||||
gic_init(0, IRQ_PPI(0), S5P_VA_GIC_DIST, S5P_VA_GIC_CPU);
|
||||
if (!of_have_populated_dt())
|
||||
gic_init(0, IRQ_PPI(0), S5P_VA_GIC_DIST, S5P_VA_GIC_CPU);
|
||||
#ifdef CONFIG_OF
|
||||
else
|
||||
of_irq_init(exynos4_dt_irq_match);
|
||||
#endif
|
||||
|
||||
gic_arch_extn.irq_eoi = exynos4_gic_irq_fix_base;
|
||||
gic_arch_extn.irq_unmask = exynos4_gic_irq_fix_base;
|
||||
gic_arch_extn.irq_mask = exynos4_gic_irq_fix_base;
|
||||
|
|
|
@ -24,6 +24,7 @@
|
|||
#include <linux/dma-mapping.h>
|
||||
#include <linux/amba/bus.h>
|
||||
#include <linux/amba/pl330.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
#include <plat/devs.h>
|
||||
|
@ -35,95 +36,42 @@
|
|||
|
||||
static u64 dma_dmamask = DMA_BIT_MASK(32);
|
||||
|
||||
struct dma_pl330_peri pdma0_peri[28] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_PCM0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ0,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ2,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0S_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART4_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART4_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS4_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS4_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_MICIN,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_PCMIN,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_PCMOUT,
|
||||
.rqtype = MEMTODEV,
|
||||
},
|
||||
u8 pdma0_peri[] = {
|
||||
DMACH_PCM0_RX,
|
||||
DMACH_PCM0_TX,
|
||||
DMACH_PCM2_RX,
|
||||
DMACH_PCM2_TX,
|
||||
DMACH_MSM_REQ0,
|
||||
DMACH_MSM_REQ2,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI2_RX,
|
||||
DMACH_SPI2_TX,
|
||||
DMACH_I2S0S_TX,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S2_RX,
|
||||
DMACH_I2S2_TX,
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART4_RX,
|
||||
DMACH_UART4_TX,
|
||||
DMACH_SLIMBUS0_RX,
|
||||
DMACH_SLIMBUS0_TX,
|
||||
DMACH_SLIMBUS2_RX,
|
||||
DMACH_SLIMBUS2_TX,
|
||||
DMACH_SLIMBUS4_RX,
|
||||
DMACH_SLIMBUS4_TX,
|
||||
DMACH_AC97_MICIN,
|
||||
DMACH_AC97_PCMIN,
|
||||
DMACH_AC97_PCMOUT,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata exynos4_pdma0_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(pdma0_peri),
|
||||
.peri = pdma0_peri,
|
||||
.peri_id = pdma0_peri,
|
||||
};
|
||||
|
||||
struct amba_device exynos4_device_pdma0 = {
|
||||
|
@ -142,86 +90,37 @@ struct amba_device exynos4_device_pdma0 = {
|
|||
.periphid = 0x00041330,
|
||||
};
|
||||
|
||||
struct dma_pl330_peri pdma1_peri[25] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_PCM0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ1,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ3,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0S_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS5_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SLIMBUS5_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
},
|
||||
u8 pdma1_peri[] = {
|
||||
DMACH_PCM0_RX,
|
||||
DMACH_PCM0_TX,
|
||||
DMACH_PCM1_RX,
|
||||
DMACH_PCM1_TX,
|
||||
DMACH_MSM_REQ1,
|
||||
DMACH_MSM_REQ3,
|
||||
DMACH_SPI1_RX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_I2S0S_TX,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S1_RX,
|
||||
DMACH_I2S1_TX,
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_SLIMBUS1_RX,
|
||||
DMACH_SLIMBUS1_TX,
|
||||
DMACH_SLIMBUS3_RX,
|
||||
DMACH_SLIMBUS3_TX,
|
||||
DMACH_SLIMBUS5_RX,
|
||||
DMACH_SLIMBUS5_TX,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata exynos4_pdma1_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(pdma1_peri),
|
||||
.peri = pdma1_peri,
|
||||
.peri_id = pdma1_peri,
|
||||
};
|
||||
|
||||
struct amba_device exynos4_device_pdma1 = {
|
||||
|
@ -242,7 +141,15 @@ struct amba_device exynos4_device_pdma1 = {
|
|||
|
||||
static int __init exynos4_dma_init(void)
|
||||
{
|
||||
if (of_have_populated_dt())
|
||||
return 0;
|
||||
|
||||
dma_cap_set(DMA_SLAVE, exynos4_pdma0_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, exynos4_pdma0_pdata.cap_mask);
|
||||
amba_device_register(&exynos4_device_pdma0, &iomem_resource);
|
||||
|
||||
dma_cap_set(DMA_SLAVE, exynos4_pdma1_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, exynos4_pdma1_pdata.cap_mask);
|
||||
amba_device_register(&exynos4_device_pdma1, &iomem_resource);
|
||||
|
||||
return 0;
|
||||
|
|
|
@ -72,7 +72,6 @@
|
|||
cmpcc \irqnr, \irqnr
|
||||
cmpne \irqnr, \tmp
|
||||
cmpcs \irqnr, \irqnr
|
||||
addne \irqnr, \irqnr, #32
|
||||
|
||||
.endm
|
||||
|
||||
|
|
|
@ -17,13 +17,13 @@
|
|||
|
||||
/* PPI: Private Peripheral Interrupt */
|
||||
|
||||
#define IRQ_PPI(x) S5P_IRQ(x+16)
|
||||
#define IRQ_PPI(x) (x+16)
|
||||
|
||||
#define IRQ_MCT_LOCALTIMER IRQ_PPI(12)
|
||||
|
||||
/* SPI: Shared Peripheral Interrupt */
|
||||
|
||||
#define IRQ_SPI(x) S5P_IRQ(x+32)
|
||||
#define IRQ_SPI(x) (x+32)
|
||||
|
||||
#define IRQ_EINT0 IRQ_SPI(16)
|
||||
#define IRQ_EINT1 IRQ_SPI(17)
|
||||
|
@ -163,7 +163,9 @@
|
|||
#define IRQ_GPIO2_NR_GROUPS 9
|
||||
#define IRQ_GPIO_END (S5P_GPIOINT_BASE + S5P_GPIOINT_COUNT)
|
||||
|
||||
#define IRQ_TIMER_BASE (IRQ_GPIO_END + 64)
|
||||
|
||||
/* Set the default NR_IRQS */
|
||||
#define NR_IRQS (IRQ_GPIO_END + 64)
|
||||
#define NR_IRQS (IRQ_TIMER_BASE + IRQ_TIMER_COUNT)
|
||||
|
||||
#endif /* __ASM_ARCH_IRQS_H */
|
||||
|
|
|
@ -14,29 +14,14 @@
|
|||
#include <plat/devs.h>
|
||||
#include <plat/regs-serial.h>
|
||||
|
||||
static struct s3c24xx_uart_clksrc exynos4_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "uclk1",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
};
|
||||
|
||||
/* uart registration process */
|
||||
void __init exynos4_common_init_uarts(struct s3c2410_uartcfg *cfg, int no)
|
||||
{
|
||||
struct s3c2410_uartcfg *tcfg = cfg;
|
||||
u32 ucnt;
|
||||
|
||||
for (ucnt = 0; ucnt < no; ucnt++, tcfg++) {
|
||||
if (!tcfg->clocks) {
|
||||
tcfg->has_fracval = 1;
|
||||
tcfg->clocks = exynos4_serial_clocks;
|
||||
tcfg->clocks_size = ARRAY_SIZE(exynos4_serial_clocks);
|
||||
}
|
||||
tcfg->flags |= NO_NEED_CHECK_CLKSRC;
|
||||
}
|
||||
for (ucnt = 0; ucnt < no; ucnt++, tcfg++)
|
||||
tcfg->has_fracval = 1;
|
||||
|
||||
s3c24xx_init_uartdevs("s5pv210-uart", s5p_uart_resources, cfg, no);
|
||||
s3c24xx_init_uartdevs("exynos4210-uart", s5p_uart_resources, cfg, no);
|
||||
}
|
||||
|
|
|
@ -0,0 +1,85 @@
|
|||
/*
|
||||
* Samsung's Exynos4210 flattened device tree enabled machine
|
||||
*
|
||||
* Copyright (c) 2010-2011 Samsung Electronics Co., Ltd.
|
||||
* http://www.samsung.com
|
||||
* Copyright (c) 2010-2011 Linaro Ltd.
|
||||
* www.linaro.org
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#include <linux/of_platform.h>
|
||||
#include <linux/serial_core.h>
|
||||
|
||||
#include <asm/mach/arch.h>
|
||||
#include <mach/map.h>
|
||||
|
||||
#include <plat/cpu.h>
|
||||
#include <plat/regs-serial.h>
|
||||
#include <plat/exynos4.h>
|
||||
|
||||
/*
|
||||
* The following lookup table is used to override device names when devices
|
||||
* are registered from device tree. This is temporarily added to enable
|
||||
* device tree support addition for the Exynos4 architecture.
|
||||
*
|
||||
* For drivers that require platform data to be provided from the machine
|
||||
* file, a platform data pointer can also be supplied along with the
|
||||
* devices names. Usually, the platform data elements that cannot be parsed
|
||||
* from the device tree by the drivers (example: function pointers) are
|
||||
* supplied. But it should be noted that this is a temporary mechanism and
|
||||
* at some point, the drivers should be capable of parsing all the platform
|
||||
* data from the device tree.
|
||||
*/
|
||||
static const struct of_dev_auxdata exynos4210_auxdata_lookup[] __initconst = {
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-uart", S5P_PA_UART0,
|
||||
"exynos4210-uart.0", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-uart", S5P_PA_UART1,
|
||||
"exynos4210-uart.1", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-uart", S5P_PA_UART2,
|
||||
"exynos4210-uart.2", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-uart", S5P_PA_UART3,
|
||||
"exynos4210-uart.3", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-sdhci", EXYNOS4_PA_HSMMC(0),
|
||||
"exynos4-sdhci.0", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-sdhci", EXYNOS4_PA_HSMMC(1),
|
||||
"exynos4-sdhci.1", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-sdhci", EXYNOS4_PA_HSMMC(2),
|
||||
"exynos4-sdhci.2", NULL),
|
||||
OF_DEV_AUXDATA("samsung,exynos4210-sdhci", EXYNOS4_PA_HSMMC(3),
|
||||
"exynos4-sdhci.3", NULL),
|
||||
OF_DEV_AUXDATA("samsung,s3c2440-i2c", EXYNOS4_PA_IIC(0),
|
||||
"s3c2440-i2c.0", NULL),
|
||||
OF_DEV_AUXDATA("arm,pl330", EXYNOS4_PA_PDMA0, "dma-pl330.0", NULL),
|
||||
OF_DEV_AUXDATA("arm,pl330", EXYNOS4_PA_PDMA1, "dma-pl330.1", NULL),
|
||||
{},
|
||||
};
|
||||
|
||||
static void __init exynos4210_dt_map_io(void)
|
||||
{
|
||||
s5p_init_io(NULL, 0, S5P_VA_CHIPID);
|
||||
s3c24xx_init_clocks(24000000);
|
||||
}
|
||||
|
||||
static void __init exynos4210_dt_machine_init(void)
|
||||
{
|
||||
of_platform_populate(NULL, of_default_bus_match_table,
|
||||
exynos4210_auxdata_lookup, NULL);
|
||||
}
|
||||
|
||||
static char const *exynos4210_dt_compat[] __initdata = {
|
||||
"samsung,exynos4210",
|
||||
NULL
|
||||
};
|
||||
|
||||
DT_MACHINE_START(EXYNOS4210_DT, "Samsung Exynos4 (Flattened Device Tree)")
|
||||
/* Maintainer: Thomas Abraham <thomas.abraham@linaro.org> */
|
||||
.init_irq = exynos4_init_irq,
|
||||
.map_io = exynos4210_dt_map_io,
|
||||
.init_machine = exynos4210_dt_machine_init,
|
||||
.timer = &exynos4_timer,
|
||||
.dt_compat = exynos4210_dt_compat,
|
||||
MACHINE_END
|
|
@ -164,22 +164,6 @@ static struct map_desc bast_iodesc[] __initdata = {
|
|||
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
|
||||
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
|
||||
|
||||
static struct s3c24xx_uart_clksrc bast_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "uclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
[1] = {
|
||||
.name = "pclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
static struct s3c2410_uartcfg bast_uartcfgs[] __initdata = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -187,8 +171,6 @@ static struct s3c2410_uartcfg bast_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = bast_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(bast_serial_clocks),
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 1,
|
||||
|
@ -196,8 +178,6 @@ static struct s3c2410_uartcfg bast_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = bast_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(bast_serial_clocks),
|
||||
},
|
||||
/* port 2 is not actually used */
|
||||
[2] = {
|
||||
|
@ -206,8 +186,6 @@ static struct s3c2410_uartcfg bast_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = bast_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(bast_serial_clocks),
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -109,23 +109,6 @@ static struct map_desc vr1000_iodesc[] __initdata = {
|
|||
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
|
||||
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
|
||||
|
||||
/* uart clock source(s) */
|
||||
|
||||
static struct s3c24xx_uart_clksrc vr1000_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "uclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
[1] = {
|
||||
.name = "pclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0.
|
||||
}
|
||||
};
|
||||
|
||||
static struct s3c2410_uartcfg vr1000_uartcfgs[] __initdata = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -133,8 +116,6 @@ static struct s3c2410_uartcfg vr1000_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = vr1000_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(vr1000_serial_clocks),
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 1,
|
||||
|
@ -142,8 +123,6 @@ static struct s3c2410_uartcfg vr1000_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = vr1000_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(vr1000_serial_clocks),
|
||||
},
|
||||
/* port 2 is not actually used */
|
||||
[2] = {
|
||||
|
@ -152,9 +131,6 @@ static struct s3c2410_uartcfg vr1000_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = vr1000_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(vr1000_serial_clocks),
|
||||
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -123,12 +123,18 @@ static struct clk s3c2410_armclk = {
|
|||
.id = -1,
|
||||
};
|
||||
|
||||
static struct clk_lookup s3c2410_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud0", &clk_p),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud1", &s3c24xx_uclk),
|
||||
};
|
||||
|
||||
void __init s3c2410_init_clocks(int xtal)
|
||||
{
|
||||
s3c24xx_register_baseclocks(xtal);
|
||||
s3c2410_setup_clocks();
|
||||
s3c2410_baseclk_add();
|
||||
s3c24xx_register_clock(&s3c2410_armclk);
|
||||
clkdev_add_table(s3c2410_clk_lookup, ARRAY_SIZE(s3c2410_clk_lookup));
|
||||
}
|
||||
|
||||
struct sysdev_class s3c2410_sysclass = {
|
||||
|
|
|
@ -659,6 +659,12 @@ static struct clk *clks[] __initdata = {
|
|||
&clk_armclk,
|
||||
};
|
||||
|
||||
static struct clk_lookup s3c2412_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud1", &s3c24xx_uclk),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_p),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &clk_usysclk),
|
||||
};
|
||||
|
||||
int __init s3c2412_baseclk_add(void)
|
||||
{
|
||||
unsigned long clkcon = __raw_readl(S3C2410_CLKCON);
|
||||
|
@ -751,6 +757,7 @@ int __init s3c2412_baseclk_add(void)
|
|||
s3c2412_clkcon_enable(clkp, 0);
|
||||
}
|
||||
|
||||
clkdev_add_table(s3c2412_clk_lookup, ARRAY_SIZE(s3c2412_clk_lookup));
|
||||
s3c_pwmclk_init();
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -34,6 +34,7 @@
|
|||
#include <linux/mutex.h>
|
||||
#include <linux/clk.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/serial_core.h>
|
||||
|
||||
#include <mach/hardware.h>
|
||||
#include <linux/atomic.h>
|
||||
|
@ -43,6 +44,7 @@
|
|||
|
||||
#include <plat/clock.h>
|
||||
#include <plat/cpu.h>
|
||||
#include <plat/regs-serial.h>
|
||||
|
||||
/* S3C2440 extended clock support */
|
||||
|
||||
|
@ -108,6 +110,46 @@ static struct clk s3c2440_clk_ac97 = {
|
|||
.ctrlbit = S3C2440_CLKCON_CAMERA,
|
||||
};
|
||||
|
||||
static unsigned long s3c2440_fclk_n_getrate(struct clk *clk)
|
||||
{
|
||||
unsigned long ucon0, ucon1, ucon2, divisor;
|
||||
|
||||
/* the fun of calculating the uart divisors on the s3c2440 */
|
||||
ucon0 = __raw_readl(S3C24XX_VA_UART0 + S3C2410_UCON);
|
||||
ucon1 = __raw_readl(S3C24XX_VA_UART1 + S3C2410_UCON);
|
||||
ucon2 = __raw_readl(S3C24XX_VA_UART2 + S3C2410_UCON);
|
||||
|
||||
ucon0 &= S3C2440_UCON0_DIVMASK;
|
||||
ucon1 &= S3C2440_UCON1_DIVMASK;
|
||||
ucon2 &= S3C2440_UCON2_DIVMASK;
|
||||
|
||||
if (ucon0 != 0)
|
||||
divisor = (ucon0 >> S3C2440_UCON_DIVSHIFT) + 6;
|
||||
else if (ucon1 != 0)
|
||||
divisor = (ucon1 >> S3C2440_UCON_DIVSHIFT) + 21;
|
||||
else if (ucon2 != 0)
|
||||
divisor = (ucon2 >> S3C2440_UCON_DIVSHIFT) + 36;
|
||||
else
|
||||
/* manual calims 44, seems to be 9 */
|
||||
divisor = 9;
|
||||
|
||||
return clk_get_rate(clk->parent) / divisor;
|
||||
}
|
||||
|
||||
static struct clk s3c2440_clk_fclk_n = {
|
||||
.name = "fclk_n",
|
||||
.parent = &clk_f,
|
||||
.ops = &(struct clk_ops) {
|
||||
.get_rate = s3c2440_fclk_n_getrate,
|
||||
},
|
||||
};
|
||||
|
||||
static struct clk_lookup s3c2440_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud1", &s3c24xx_uclk),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_p),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &s3c2440_clk_fclk_n),
|
||||
};
|
||||
|
||||
static int s3c2440_clk_add(struct sys_device *sysdev)
|
||||
{
|
||||
struct clk *clock_upll;
|
||||
|
@ -126,10 +168,12 @@ static int s3c2440_clk_add(struct sys_device *sysdev)
|
|||
s3c2440_clk_cam.parent = clock_h;
|
||||
s3c2440_clk_ac97.parent = clock_p;
|
||||
s3c2440_clk_cam_upll.parent = clock_upll;
|
||||
s3c24xx_register_clock(&s3c2440_clk_fclk_n);
|
||||
|
||||
s3c24xx_register_clock(&s3c2440_clk_ac97);
|
||||
s3c24xx_register_clock(&s3c2440_clk_cam);
|
||||
s3c24xx_register_clock(&s3c2440_clk_cam_upll);
|
||||
clkdev_add_table(s3c2440_clk_lookup, ARRAY_SIZE(s3c2440_clk_lookup));
|
||||
|
||||
clk_disable(&s3c2440_clk_ac97);
|
||||
clk_disable(&s3c2440_clk_cam);
|
||||
|
|
|
@ -96,22 +96,6 @@ static struct map_desc anubis_iodesc[] __initdata = {
|
|||
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
|
||||
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
|
||||
|
||||
static struct s3c24xx_uart_clksrc anubis_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "uclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
[1] = {
|
||||
.name = "pclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
static struct s3c2410_uartcfg anubis_uartcfgs[] __initdata = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -119,8 +103,7 @@ static struct s3c2410_uartcfg anubis_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = anubis_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(anubis_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 2,
|
||||
|
@ -128,8 +111,7 @@ static struct s3c2410_uartcfg anubis_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = anubis_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(anubis_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
},
|
||||
};
|
||||
|
||||
|
|
|
@ -57,22 +57,6 @@ static struct map_desc at2440evb_iodesc[] __initdata = {
|
|||
#define ULCON (S3C2410_LCON_CS8 | S3C2410_LCON_PNONE)
|
||||
#define UFCON (S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE)
|
||||
|
||||
static struct s3c24xx_uart_clksrc at2440evb_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "uclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
[1] = {
|
||||
.name = "pclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
static struct s3c2410_uartcfg at2440evb_uartcfgs[] __initdata = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -80,8 +64,7 @@ static struct s3c2410_uartcfg at2440evb_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = at2440evb_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(at2440evb_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 1,
|
||||
|
@ -89,8 +72,7 @@ static struct s3c2410_uartcfg at2440evb_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = at2440evb_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(at2440evb_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
},
|
||||
};
|
||||
|
||||
|
|
|
@ -100,21 +100,6 @@ static struct map_desc osiris_iodesc[] __initdata = {
|
|||
#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
|
||||
#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
|
||||
|
||||
static struct s3c24xx_uart_clksrc osiris_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "uclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
[1] = {
|
||||
.name = "pclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
}
|
||||
};
|
||||
|
||||
static struct s3c2410_uartcfg osiris_uartcfgs[] __initdata = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -122,8 +107,7 @@ static struct s3c2410_uartcfg osiris_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = osiris_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(osiris_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 1,
|
||||
|
@ -131,8 +115,7 @@ static struct s3c2410_uartcfg osiris_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = osiris_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(osiris_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
},
|
||||
[2] = {
|
||||
.hwport = 2,
|
||||
|
@ -140,8 +123,7 @@ static struct s3c2410_uartcfg osiris_uartcfgs[] __initdata = {
|
|||
.ucon = UCON,
|
||||
.ulcon = ULCON,
|
||||
.ufcon = UFCON,
|
||||
.clocks = osiris_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(osiris_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL1 | S3C2410_UCON_CLKSEL2,
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -68,15 +68,6 @@
|
|||
static struct map_desc rx1950_iodesc[] __initdata = {
|
||||
};
|
||||
|
||||
static struct s3c24xx_uart_clksrc rx1950_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "fclk",
|
||||
.divisor = 0x0a,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
};
|
||||
|
||||
static struct s3c2410_uartcfg rx1950_uartcfgs[] __initdata = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -84,8 +75,7 @@ static struct s3c2410_uartcfg rx1950_uartcfgs[] __initdata = {
|
|||
.ucon = 0x3c5,
|
||||
.ulcon = 0x03,
|
||||
.ufcon = 0x51,
|
||||
.clocks = rx1950_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(rx1950_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL3,
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 1,
|
||||
|
@ -93,8 +83,7 @@ static struct s3c2410_uartcfg rx1950_uartcfgs[] __initdata = {
|
|||
.ucon = 0x3c5,
|
||||
.ulcon = 0x03,
|
||||
.ufcon = 0x51,
|
||||
.clocks = rx1950_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(rx1950_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL3,
|
||||
},
|
||||
/* IR port */
|
||||
[2] = {
|
||||
|
@ -103,8 +92,7 @@ static struct s3c2410_uartcfg rx1950_uartcfgs[] __initdata = {
|
|||
.ucon = 0x3c5,
|
||||
.ulcon = 0x43,
|
||||
.ufcon = 0xf1,
|
||||
.clocks = rx1950_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(rx1950_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL3,
|
||||
},
|
||||
};
|
||||
|
||||
|
|
|
@ -67,16 +67,6 @@ static struct map_desc rx3715_iodesc[] __initdata = {
|
|||
},
|
||||
};
|
||||
|
||||
|
||||
static struct s3c24xx_uart_clksrc rx3715_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "fclk",
|
||||
.divisor = 0,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
}
|
||||
};
|
||||
|
||||
static struct s3c2410_uartcfg rx3715_uartcfgs[] = {
|
||||
[0] = {
|
||||
.hwport = 0,
|
||||
|
@ -84,8 +74,7 @@ static struct s3c2410_uartcfg rx3715_uartcfgs[] = {
|
|||
.ucon = 0x3c5,
|
||||
.ulcon = 0x03,
|
||||
.ufcon = 0x51,
|
||||
.clocks = rx3715_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(rx3715_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL3,
|
||||
},
|
||||
[1] = {
|
||||
.hwport = 1,
|
||||
|
@ -93,8 +82,7 @@ static struct s3c2410_uartcfg rx3715_uartcfgs[] = {
|
|||
.ucon = 0x3c5,
|
||||
.ulcon = 0x03,
|
||||
.ufcon = 0x00,
|
||||
.clocks = rx3715_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(rx3715_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL3,
|
||||
},
|
||||
/* IR port */
|
||||
[2] = {
|
||||
|
@ -103,8 +91,7 @@ static struct s3c2410_uartcfg rx3715_uartcfgs[] = {
|
|||
.ucon = 0x3c5,
|
||||
.ulcon = 0x43,
|
||||
.ufcon = 0x51,
|
||||
.clocks = rx3715_serial_clocks,
|
||||
.clocks_size = ARRAY_SIZE(rx3715_serial_clocks),
|
||||
.clk_sel = S3C2410_UCON_CLKSEL3,
|
||||
}
|
||||
};
|
||||
|
||||
|
|
|
@ -616,16 +616,6 @@ static struct clksrc_clk clksrcs[] = {
|
|||
.reg_div = { .reg = S3C_CLK_DIV1, .shift = 20, .size = 4 },
|
||||
.sources = &clkset_uhost,
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = S3C_CLKCON_SCLK_UART,
|
||||
.enable = s3c64xx_sclk_ctrl,
|
||||
},
|
||||
.reg_src = { .reg = S3C_CLK_SRC, .shift = 13, .size = 1 },
|
||||
.reg_div = { .reg = S3C_CLK_DIV2, .shift = 16, .size = 4 },
|
||||
.sources = &clkset_uart,
|
||||
}, {
|
||||
/* Where does UCLK0 come from? */
|
||||
.clk = {
|
||||
.name = "spi-bus",
|
||||
.devname = "s3c64xx-spi.0",
|
||||
|
@ -695,6 +685,18 @@ static struct clksrc_clk clksrcs[] = {
|
|||
},
|
||||
};
|
||||
|
||||
/* Where does UCLK0 come from? */
|
||||
static struct clksrc_clk clk_sclk_uclk = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = S3C_CLKCON_SCLK_UART,
|
||||
.enable = s3c64xx_sclk_ctrl,
|
||||
},
|
||||
.reg_src = { .reg = S3C_CLK_SRC, .shift = 13, .size = 1 },
|
||||
.reg_div = { .reg = S3C_CLK_DIV2, .shift = 16, .size = 4 },
|
||||
.sources = &clkset_uart,
|
||||
};
|
||||
|
||||
/* Clock initialisation code */
|
||||
|
||||
static struct clksrc_clk *init_parents[] = {
|
||||
|
@ -703,6 +705,15 @@ static struct clksrc_clk *init_parents[] = {
|
|||
&clk_mout_mpll,
|
||||
};
|
||||
|
||||
static struct clksrc_clk *clksrc_cdev[] = {
|
||||
&clk_sclk_uclk,
|
||||
};
|
||||
|
||||
static struct clk_lookup s3c64xx_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_p),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &clk_sclk_uclk.clk),
|
||||
};
|
||||
|
||||
#define GET_DIV(clk, field) ((((clk) & field##_MASK) >> field##_SHIFT) + 1)
|
||||
|
||||
void __init_or_cpufreq s3c6400_setup_clocks(void)
|
||||
|
@ -811,6 +822,8 @@ static struct clk *clks[] __initdata = {
|
|||
void __init s3c64xx_register_clocks(unsigned long xtal,
|
||||
unsigned armclk_divlimit)
|
||||
{
|
||||
unsigned int cnt;
|
||||
|
||||
armclk_mask = armclk_divlimit;
|
||||
|
||||
s3c24xx_register_baseclocks(xtal);
|
||||
|
@ -823,5 +836,9 @@ void __init s3c64xx_register_clocks(unsigned long xtal,
|
|||
|
||||
s3c24xx_register_clocks(clks1, ARRAY_SIZE(clks1));
|
||||
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
|
||||
for (cnt = 0; cnt < ARRAY_SIZE(clksrc_cdev); cnt++)
|
||||
s3c_register_clksrc(clksrc_cdev[cnt], 1);
|
||||
clkdev_add_table(s3c64xx_clk_lookup, ARRAY_SIZE(s3c64xx_clk_lookup));
|
||||
|
||||
s3c_pwmclk_init();
|
||||
}
|
||||
|
|
|
@ -419,15 +419,6 @@ static struct clksrc_clk clksrcs[] = {
|
|||
.sources = &clkset_group1,
|
||||
.reg_src = { .reg = S5P64X0_CLK_SRC0, .shift = 22, .size = 2 },
|
||||
.reg_div = { .reg = S5P64X0_CLK_DIV1, .shift = 8, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = (1 << 5),
|
||||
.enable = s5p64x0_sclk_ctrl,
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P64X0_CLK_SRC0, .shift = 13, .size = 1 },
|
||||
.reg_div = { .reg = S5P64X0_CLK_DIV2, .shift = 16, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "sclk_spi",
|
||||
|
@ -487,6 +478,17 @@ static struct clksrc_clk clksrcs[] = {
|
|||
},
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uclk = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = (1 << 5),
|
||||
.enable = s5p64x0_sclk_ctrl,
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P64X0_CLK_SRC0, .shift = 13, .size = 1 },
|
||||
.reg_div = { .reg = S5P64X0_CLK_DIV2, .shift = 16, .size = 4 },
|
||||
};
|
||||
|
||||
/* Clock initialization code */
|
||||
static struct clksrc_clk *sysclks[] = {
|
||||
&clk_mout_apll,
|
||||
|
@ -505,6 +507,15 @@ static struct clk dummy_apb_pclk = {
|
|||
.id = -1,
|
||||
};
|
||||
|
||||
static struct clksrc_clk *clksrc_cdev[] = {
|
||||
&clk_sclk_uclk,
|
||||
};
|
||||
|
||||
static struct clk_lookup s5p6440_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_pclk_low.clk),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &clk_sclk_uclk.clk),
|
||||
};
|
||||
|
||||
void __init_or_cpufreq s5p6440_setup_clocks(void)
|
||||
{
|
||||
struct clk *xtal_clk;
|
||||
|
@ -583,9 +594,12 @@ void __init s5p6440_register_clocks(void)
|
|||
|
||||
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
|
||||
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
|
||||
for (ptr = 0; ptr < ARRAY_SIZE(clksrc_cdev); ptr++)
|
||||
s3c_register_clksrc(clksrc_cdev[ptr], 1);
|
||||
|
||||
s3c_register_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
s3c_disable_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
clkdev_add_table(s5p6440_clk_lookup, ARRAY_SIZE(s5p6440_clk_lookup));
|
||||
|
||||
s3c24xx_register_clock(&dummy_apb_pclk);
|
||||
|
||||
|
|
|
@ -441,15 +441,6 @@ static struct clksrc_clk clksrcs[] = {
|
|||
.sources = &clkset_group2,
|
||||
.reg_src = { .reg = S5P64X0_CLK_SRC0, .shift = 22, .size = 2 },
|
||||
.reg_div = { .reg = S5P64X0_CLK_DIV1, .shift = 8, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = (1 << 5),
|
||||
.enable = s5p64x0_sclk_ctrl,
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P64X0_CLK_SRC0, .shift = 13, .size = 1 },
|
||||
.reg_div = { .reg = S5P64X0_CLK_DIV2, .shift = 16, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "sclk_spi",
|
||||
|
@ -536,6 +527,26 @@ static struct clksrc_clk clksrcs[] = {
|
|||
},
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uclk = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = (1 << 5),
|
||||
.enable = s5p64x0_sclk_ctrl,
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P64X0_CLK_SRC0, .shift = 13, .size = 1 },
|
||||
.reg_div = { .reg = S5P64X0_CLK_DIV2, .shift = 16, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk *clksrc_cdev[] = {
|
||||
&clk_sclk_uclk,
|
||||
};
|
||||
|
||||
static struct clk_lookup s5p6450_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_pclk_low.clk),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &clk_sclk_uclk.clk),
|
||||
};
|
||||
|
||||
/* Clock initialization code */
|
||||
static struct clksrc_clk *sysclks[] = {
|
||||
&clk_mout_apll,
|
||||
|
@ -634,9 +645,12 @@ void __init s5p6450_register_clocks(void)
|
|||
|
||||
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
|
||||
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
|
||||
for (ptr = 0; ptr < ARRAY_SIZE(clksrc_cdev); ptr++)
|
||||
s3c_register_clksrc(clksrc_cdev[ptr], 1);
|
||||
|
||||
s3c_register_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
s3c_disable_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
clkdev_add_table(s5p6450_clk_lookup, ARRAY_SIZE(s5p6450_clk_lookup));
|
||||
|
||||
s3c24xx_register_clock(&dummy_apb_pclk);
|
||||
|
||||
|
|
|
@ -38,176 +38,74 @@
|
|||
|
||||
static u64 dma_dmamask = DMA_BIT_MASK(32);
|
||||
|
||||
struct dma_pl330_peri s5p6440_pdma_peri[22] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
},
|
||||
u8 s5p6440_pdma_peri[] = {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_PCM0_TX,
|
||||
DMACH_PCM0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_SPI1_RX,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata s5p6440_pdma_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(s5p6440_pdma_peri),
|
||||
.peri = s5p6440_pdma_peri,
|
||||
.peri_id = s5p6440_pdma_peri,
|
||||
};
|
||||
|
||||
struct dma_pl330_peri s5p6450_pdma_peri[32] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART4_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART4_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_USI_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_USI_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PWM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART5_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART5_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
},
|
||||
u8 s5p6450_pdma_peri[] = {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_UART4_RX,
|
||||
DMACH_UART4_TX,
|
||||
DMACH_PCM0_TX,
|
||||
DMACH_PCM0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_PCM1_TX,
|
||||
DMACH_PCM1_RX,
|
||||
DMACH_PCM2_TX,
|
||||
DMACH_PCM2_RX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_SPI1_RX,
|
||||
DMACH_USI_TX,
|
||||
DMACH_USI_RX,
|
||||
DMACH_MAX,
|
||||
DMACH_I2S1_TX,
|
||||
DMACH_I2S1_RX,
|
||||
DMACH_I2S2_TX,
|
||||
DMACH_I2S2_RX,
|
||||
DMACH_PWM,
|
||||
DMACH_UART5_RX,
|
||||
DMACH_UART5_TX,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata s5p6450_pdma_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(s5p6450_pdma_peri),
|
||||
.peri = s5p6450_pdma_peri,
|
||||
.peri_id = s5p6450_pdma_peri,
|
||||
};
|
||||
|
||||
struct amba_device s5p64x0_device_pdma = {
|
||||
|
@ -227,10 +125,15 @@ struct amba_device s5p64x0_device_pdma = {
|
|||
|
||||
static int __init s5p64x0_dma_init(void)
|
||||
{
|
||||
if (soc_is_s5p6450())
|
||||
if (soc_is_s5p6450()) {
|
||||
dma_cap_set(DMA_SLAVE, s5p6450_pdma_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, s5p6450_pdma_pdata.cap_mask);
|
||||
s5p64x0_device_pdma.dev.platform_data = &s5p6450_pdma_pdata;
|
||||
else
|
||||
} else {
|
||||
dma_cap_set(DMA_SLAVE, s5p6440_pdma_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, s5p6440_pdma_pdata.cap_mask);
|
||||
s5p64x0_device_pdma.dev.platform_data = &s5p6440_pdma_pdata;
|
||||
}
|
||||
|
||||
amba_device_register(&s5p64x0_device_pdma, &iomem_resource);
|
||||
|
||||
|
|
|
@ -141,6 +141,8 @@
|
|||
|
||||
#define IRQ_EINT_GROUP(grp, x) (IRQ_EINT_GROUP##grp##_BASE + (x))
|
||||
|
||||
#define IRQ_TIMER_BASE (11)
|
||||
|
||||
/* Set the default NR_IRQS */
|
||||
|
||||
#define NR_IRQS (IRQ_EINT_GROUP8_BASE + IRQ_EINT_GROUP8_NR + 1)
|
||||
|
|
|
@ -23,36 +23,7 @@
|
|||
#include <plat/s5p6450.h>
|
||||
#include <plat/regs-serial.h>
|
||||
|
||||
static struct s3c24xx_uart_clksrc s5p64x0_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "pclk_low",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
[1] = {
|
||||
.name = "uclk1",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
};
|
||||
|
||||
/* uart registration process */
|
||||
|
||||
void __init s5p64x0_common_init_uarts(struct s3c2410_uartcfg *cfg, int no)
|
||||
{
|
||||
struct s3c2410_uartcfg *tcfg = cfg;
|
||||
u32 ucnt;
|
||||
|
||||
for (ucnt = 0; ucnt < no; ucnt++, tcfg++) {
|
||||
if (!tcfg->clocks) {
|
||||
tcfg->clocks = s5p64x0_serial_clocks;
|
||||
tcfg->clocks_size = ARRAY_SIZE(s5p64x0_serial_clocks);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void __init s5p6440_init_uarts(struct s3c2410_uartcfg *cfg, int no)
|
||||
{
|
||||
int uart;
|
||||
|
@ -62,12 +33,10 @@ void __init s5p6440_init_uarts(struct s3c2410_uartcfg *cfg, int no)
|
|||
s5p_uart_resources[uart].resources->end = S5P6440_PA_UART(uart) + S5P_SZ_UART;
|
||||
}
|
||||
|
||||
s5p64x0_common_init_uarts(cfg, no);
|
||||
s3c24xx_init_uartdevs("s3c6400-uart", s5p_uart_resources, cfg, no);
|
||||
}
|
||||
|
||||
void __init s5p6450_init_uarts(struct s3c2410_uartcfg *cfg, int no)
|
||||
{
|
||||
s5p64x0_common_init_uarts(cfg, no);
|
||||
s3c24xx_init_uartdevs("s3c6400-uart", s5p_uart_resources, cfg, no);
|
||||
}
|
||||
|
|
|
@ -960,16 +960,6 @@ static struct clksrc_clk clksrcs[] = {
|
|||
.sources = &clk_src_group1,
|
||||
.reg_src = { .reg = S5P_CLK_SRC1, .shift = 12, .size = 2 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV2, .shift = 12, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = (1 << 3),
|
||||
.enable = s5pc100_sclk0_ctrl,
|
||||
|
||||
},
|
||||
.sources = &clk_src_group2,
|
||||
.reg_src = { .reg = S5P_CLK_SRC1, .shift = 0, .size = 1 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV2, .shift = 0, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "sclk_mixer",
|
||||
|
@ -1098,6 +1088,17 @@ static struct clksrc_clk clksrcs[] = {
|
|||
},
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.ctrlbit = (1 << 3),
|
||||
.enable = s5pc100_sclk0_ctrl,
|
||||
},
|
||||
.sources = &clk_src_group2,
|
||||
.reg_src = { .reg = S5P_CLK_SRC1, .shift = 0, .size = 1 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV2, .shift = 0, .size = 4 },
|
||||
};
|
||||
|
||||
/* Clock initialisation code */
|
||||
static struct clksrc_clk *sysclks[] = {
|
||||
&clk_mout_apll,
|
||||
|
@ -1127,6 +1128,10 @@ static struct clksrc_clk *sysclks[] = {
|
|||
&clk_sclk_spdif,
|
||||
};
|
||||
|
||||
static struct clksrc_clk *clksrc_cdev[] = {
|
||||
&clk_sclk_uart,
|
||||
};
|
||||
|
||||
void __init_or_cpufreq s5pc100_setup_clocks(void)
|
||||
{
|
||||
unsigned long xtal;
|
||||
|
@ -1266,6 +1271,11 @@ static struct clk *clks[] __initdata = {
|
|||
&clk_pcmcdclk1,
|
||||
};
|
||||
|
||||
static struct clk_lookup s5pc100_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_p),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &clk_sclk_uart.clk),
|
||||
};
|
||||
|
||||
void __init s5pc100_register_clocks(void)
|
||||
{
|
||||
int ptr;
|
||||
|
@ -1277,9 +1287,12 @@ void __init s5pc100_register_clocks(void)
|
|||
|
||||
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
|
||||
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
|
||||
for (ptr = 0; ptr < ARRAY_SIZE(clksrc_cdev); ptr++)
|
||||
s3c_register_clksrc(clksrc_cdev[ptr], 1);
|
||||
|
||||
s3c_register_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
s3c_disable_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
clkdev_add_table(s5pc100_clk_lookup, ARRAY_SIZE(s5pc100_clk_lookup));
|
||||
|
||||
s3c24xx_register_clock(&dummy_apb_pclk);
|
||||
|
||||
|
|
|
@ -35,100 +35,42 @@
|
|||
|
||||
static u64 dma_dmamask = DMA_BIT_MASK(32);
|
||||
|
||||
struct dma_pl330_peri pdma0_peri[30] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = DMACH_IRDA,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0S_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_MICIN,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_PCMIN,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_PCMOUT,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_EXTERNAL,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PWM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPDIF,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_HSI_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_HSI_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
},
|
||||
u8 pdma0_peri[] = {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_IRDA,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S0S_TX,
|
||||
DMACH_I2S1_RX,
|
||||
DMACH_I2S1_TX,
|
||||
DMACH_I2S2_RX,
|
||||
DMACH_I2S2_TX,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI1_RX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_SPI2_RX,
|
||||
DMACH_SPI2_TX,
|
||||
DMACH_AC97_MICIN,
|
||||
DMACH_AC97_PCMIN,
|
||||
DMACH_AC97_PCMOUT,
|
||||
DMACH_EXTERNAL,
|
||||
DMACH_PWM,
|
||||
DMACH_SPDIF,
|
||||
DMACH_HSI_RX,
|
||||
DMACH_HSI_TX,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata s5pc100_pdma0_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(pdma0_peri),
|
||||
.peri = pdma0_peri,
|
||||
.peri_id = pdma0_peri,
|
||||
};
|
||||
|
||||
struct amba_device s5pc100_device_pdma0 = {
|
||||
|
@ -147,98 +89,42 @@ struct amba_device s5pc100_device_pdma0 = {
|
|||
.periphid = 0x00041330,
|
||||
};
|
||||
|
||||
struct dma_pl330_peri pdma1_peri[30] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = DMACH_IRDA,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0S_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ0,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ1,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ2,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ3,
|
||||
},
|
||||
u8 pdma1_peri[] = {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_IRDA,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S0S_TX,
|
||||
DMACH_I2S1_RX,
|
||||
DMACH_I2S1_TX,
|
||||
DMACH_I2S2_RX,
|
||||
DMACH_I2S2_TX,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI1_RX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_SPI2_RX,
|
||||
DMACH_SPI2_TX,
|
||||
DMACH_PCM0_RX,
|
||||
DMACH_PCM0_TX,
|
||||
DMACH_PCM1_RX,
|
||||
DMACH_PCM1_TX,
|
||||
DMACH_MSM_REQ0,
|
||||
DMACH_MSM_REQ1,
|
||||
DMACH_MSM_REQ2,
|
||||
DMACH_MSM_REQ3,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata s5pc100_pdma1_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(pdma1_peri),
|
||||
.peri = pdma1_peri,
|
||||
.peri_id = pdma1_peri,
|
||||
};
|
||||
|
||||
struct amba_device s5pc100_device_pdma1 = {
|
||||
|
@ -259,7 +145,12 @@ struct amba_device s5pc100_device_pdma1 = {
|
|||
|
||||
static int __init s5pc100_dma_init(void)
|
||||
{
|
||||
dma_cap_set(DMA_SLAVE, s5pc100_pdma0_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, s5pc100_pdma0_pdata.cap_mask);
|
||||
amba_device_register(&s5pc100_device_pdma0, &iomem_resource);
|
||||
|
||||
dma_cap_set(DMA_SLAVE, s5pc100_pdma1_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, s5pc100_pdma1_pdata.cap_mask);
|
||||
amba_device_register(&s5pc100_device_pdma1, &iomem_resource);
|
||||
|
||||
return 0;
|
||||
|
|
|
@ -97,6 +97,8 @@
|
|||
#define IRQ_SDMFIQ S5P_IRQ_VIC2(31)
|
||||
#define IRQ_VIC_END S5P_IRQ_VIC2(31)
|
||||
|
||||
#define IRQ_TIMER_BASE (11)
|
||||
|
||||
#define S5P_EINT_BASE1 (S5P_IRQ_VIC0(0))
|
||||
#define S5P_EINT_BASE2 (IRQ_VIC_END + 1)
|
||||
|
||||
|
|
|
@ -807,46 +807,6 @@ static struct clksrc_clk clksrcs[] = {
|
|||
.sources = &clkset_sclk_onenand,
|
||||
.reg_src = { .reg = S5P_CLK_SRC0, .shift = 28, .size = 1 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV6, .shift = 12, .size = 3 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.0",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 12),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 16, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 16, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.1",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 13),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 20, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 20, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.2",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 14),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 24, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 24, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.3",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 15),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 28, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 28, .size = 4 },
|
||||
}, {
|
||||
.clk = {
|
||||
.name = "sclk_fimc",
|
||||
|
@ -1022,6 +982,61 @@ static struct clksrc_clk clksrcs[] = {
|
|||
},
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart0 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.0",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 12),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 16, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 16, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart1 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.1",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 13),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 20, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 20, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart2 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.2",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 14),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 24, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 24, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_sclk_uart3 = {
|
||||
.clk = {
|
||||
.name = "uclk1",
|
||||
.devname = "s5pv210-uart.3",
|
||||
.enable = s5pv210_clk_mask0_ctrl,
|
||||
.ctrlbit = (1 << 15),
|
||||
},
|
||||
.sources = &clkset_uart,
|
||||
.reg_src = { .reg = S5P_CLK_SRC4, .shift = 28, .size = 4 },
|
||||
.reg_div = { .reg = S5P_CLK_DIV4, .shift = 28, .size = 4 },
|
||||
};
|
||||
|
||||
static struct clksrc_clk *clksrc_cdev[] = {
|
||||
&clk_sclk_uart0,
|
||||
&clk_sclk_uart1,
|
||||
&clk_sclk_uart2,
|
||||
&clk_sclk_uart3,
|
||||
};
|
||||
|
||||
/* Clock initialisation code */
|
||||
static struct clksrc_clk *sysclks[] = {
|
||||
&clk_mout_apll,
|
||||
|
@ -1261,6 +1276,14 @@ static struct clk *clks[] __initdata = {
|
|||
&clk_pcmcdclk2,
|
||||
};
|
||||
|
||||
static struct clk_lookup s5pv210_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud0", &clk_p),
|
||||
CLKDEV_INIT("s5pv210-uart.0", "clk_uart_baud1", &clk_sclk_uart0.clk),
|
||||
CLKDEV_INIT("s5pv210-uart.1", "clk_uart_baud1", &clk_sclk_uart1.clk),
|
||||
CLKDEV_INIT("s5pv210-uart.2", "clk_uart_baud1", &clk_sclk_uart2.clk),
|
||||
CLKDEV_INIT("s5pv210-uart.3", "clk_uart_baud1", &clk_sclk_uart3.clk),
|
||||
};
|
||||
|
||||
void __init s5pv210_register_clocks(void)
|
||||
{
|
||||
int ptr;
|
||||
|
@ -1273,11 +1296,15 @@ void __init s5pv210_register_clocks(void)
|
|||
for (ptr = 0; ptr < ARRAY_SIZE(sclk_tv); ptr++)
|
||||
s3c_register_clksrc(sclk_tv[ptr], 1);
|
||||
|
||||
for (ptr = 0; ptr < ARRAY_SIZE(clksrc_cdev); ptr++)
|
||||
s3c_register_clksrc(clksrc_cdev[ptr], 1);
|
||||
|
||||
s3c_register_clksrc(clksrcs, ARRAY_SIZE(clksrcs));
|
||||
s3c_register_clocks(init_clocks, ARRAY_SIZE(init_clocks));
|
||||
|
||||
s3c_register_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
s3c_disable_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
clkdev_add_table(s5pv210_clk_lookup, ARRAY_SIZE(s5pv210_clk_lookup));
|
||||
|
||||
s3c24xx_register_clock(&dummy_apb_pclk);
|
||||
s3c_pwmclk_init();
|
||||
|
|
|
@ -35,90 +35,40 @@
|
|||
|
||||
static u64 dma_dmamask = DMA_BIT_MASK(32);
|
||||
|
||||
struct dma_pl330_peri pdma0_peri[28] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0S_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_MICIN,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_PCMIN,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_AC97_PCMOUT,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PWM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPDIF,
|
||||
.rqtype = MEMTODEV,
|
||||
},
|
||||
u8 pdma0_peri[] = {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_MAX,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S0S_TX,
|
||||
DMACH_I2S1_RX,
|
||||
DMACH_I2S1_TX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI1_RX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_AC97_MICIN,
|
||||
DMACH_AC97_PCMIN,
|
||||
DMACH_AC97_PCMOUT,
|
||||
DMACH_MAX,
|
||||
DMACH_PWM,
|
||||
DMACH_SPDIF,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata s5pv210_pdma0_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(pdma0_peri),
|
||||
.peri = pdma0_peri,
|
||||
.peri_id = pdma0_peri,
|
||||
};
|
||||
|
||||
struct amba_device s5pv210_device_pdma0 = {
|
||||
|
@ -137,102 +87,44 @@ struct amba_device s5pv210_device_pdma0 = {
|
|||
.periphid = 0x00041330,
|
||||
};
|
||||
|
||||
struct dma_pl330_peri pdma1_peri[32] = {
|
||||
{
|
||||
.peri_id = (u8)DMACH_UART0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_UART3_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S0S_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_I2S2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_SPI1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MAX,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM0_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM1_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ0,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ1,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ2,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_MSM_REQ3,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM2_RX,
|
||||
.rqtype = DEVTOMEM,
|
||||
}, {
|
||||
.peri_id = (u8)DMACH_PCM2_TX,
|
||||
.rqtype = MEMTODEV,
|
||||
},
|
||||
u8 pdma1_peri[] = {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
DMACH_UART2_RX,
|
||||
DMACH_UART2_TX,
|
||||
DMACH_UART3_RX,
|
||||
DMACH_UART3_TX,
|
||||
DMACH_MAX,
|
||||
DMACH_I2S0_RX,
|
||||
DMACH_I2S0_TX,
|
||||
DMACH_I2S0S_TX,
|
||||
DMACH_I2S1_RX,
|
||||
DMACH_I2S1_TX,
|
||||
DMACH_I2S2_RX,
|
||||
DMACH_I2S2_TX,
|
||||
DMACH_SPI0_RX,
|
||||
DMACH_SPI0_TX,
|
||||
DMACH_SPI1_RX,
|
||||
DMACH_SPI1_TX,
|
||||
DMACH_MAX,
|
||||
DMACH_MAX,
|
||||
DMACH_PCM0_RX,
|
||||
DMACH_PCM0_TX,
|
||||
DMACH_PCM1_RX,
|
||||
DMACH_PCM1_TX,
|
||||
DMACH_MSM_REQ0,
|
||||
DMACH_MSM_REQ1,
|
||||
DMACH_MSM_REQ2,
|
||||
DMACH_MSM_REQ3,
|
||||
DMACH_PCM2_RX,
|
||||
DMACH_PCM2_TX,
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata s5pv210_pdma1_pdata = {
|
||||
.nr_valid_peri = ARRAY_SIZE(pdma1_peri),
|
||||
.peri = pdma1_peri,
|
||||
.peri_id = pdma1_peri,
|
||||
};
|
||||
|
||||
struct amba_device s5pv210_device_pdma1 = {
|
||||
|
@ -253,7 +145,12 @@ struct amba_device s5pv210_device_pdma1 = {
|
|||
|
||||
static int __init s5pv210_dma_init(void)
|
||||
{
|
||||
dma_cap_set(DMA_SLAVE, s5pv210_pdma0_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, s5pv210_pdma0_pdata.cap_mask);
|
||||
amba_device_register(&s5pv210_device_pdma0, &iomem_resource);
|
||||
|
||||
dma_cap_set(DMA_SLAVE, s5pv210_pdma1_pdata.cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, s5pv210_pdma1_pdata.cap_mask);
|
||||
amba_device_register(&s5pv210_device_pdma1, &iomem_resource);
|
||||
|
||||
return 0;
|
||||
|
|
|
@ -118,6 +118,8 @@
|
|||
#define IRQ_MDNIE3 S5P_IRQ_VIC3(8)
|
||||
#define IRQ_VIC_END S5P_IRQ_VIC3(31)
|
||||
|
||||
#define IRQ_TIMER_BASE (11)
|
||||
|
||||
#define S5P_EINT_BASE1 (S5P_IRQ_VIC0(0))
|
||||
#define S5P_EINT_BASE2 (IRQ_VIC_END + 1)
|
||||
|
||||
|
|
|
@ -18,27 +18,8 @@
|
|||
#include <plat/s5pv210.h>
|
||||
#include <plat/regs-serial.h>
|
||||
|
||||
static struct s3c24xx_uart_clksrc s5pv210_serial_clocks[] = {
|
||||
[0] = {
|
||||
.name = "pclk",
|
||||
.divisor = 1,
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
},
|
||||
};
|
||||
|
||||
/* uart registration process */
|
||||
void __init s5pv210_common_init_uarts(struct s3c2410_uartcfg *cfg, int no)
|
||||
{
|
||||
struct s3c2410_uartcfg *tcfg = cfg;
|
||||
u32 ucnt;
|
||||
|
||||
for (ucnt = 0; ucnt < no; ucnt++, tcfg++) {
|
||||
if (!tcfg->clocks) {
|
||||
tcfg->clocks = s5pv210_serial_clocks;
|
||||
tcfg->clocks_size = ARRAY_SIZE(s5pv210_serial_clocks);
|
||||
}
|
||||
}
|
||||
|
||||
s3c24xx_init_uartdevs("s5pv210-uart", s5p_uart_resources, cfg, no);
|
||||
}
|
||||
|
|
|
@ -297,13 +297,6 @@ static struct clksrc_clk clk_usb_bus_host = {
|
|||
|
||||
static struct clksrc_clk clksrc_clks[] = {
|
||||
{
|
||||
/* ART baud-rate clock sourced from esysclk via a divisor */
|
||||
.clk = {
|
||||
.name = "uartclk",
|
||||
.parent = &clk_esysclk.clk,
|
||||
},
|
||||
.reg_div = { .reg = S3C2443_CLKDIV1, .size = 4, .shift = 8 },
|
||||
}, {
|
||||
/* camera interface bus-clock, divided down from esysclk */
|
||||
.clk = {
|
||||
.name = "camif-upll", /* same as 2440 name */
|
||||
|
@ -323,6 +316,15 @@ static struct clksrc_clk clksrc_clks[] = {
|
|||
},
|
||||
};
|
||||
|
||||
static struct clksrc_clk clk_esys_uart = {
|
||||
/* ART baud-rate clock sourced from esysclk via a divisor */
|
||||
.clk = {
|
||||
.name = "uartclk",
|
||||
.parent = &clk_esysclk.clk,
|
||||
},
|
||||
.reg_div = { .reg = S3C2443_CLKDIV1, .size = 4, .shift = 8 },
|
||||
};
|
||||
|
||||
static struct clk clk_i2s_ext = {
|
||||
.name = "i2s-ext",
|
||||
};
|
||||
|
@ -589,6 +591,12 @@ static struct clksrc_clk *clksrcs[] __initdata = {
|
|||
&clk_arm,
|
||||
};
|
||||
|
||||
static struct clk_lookup s3c2443_clk_lookup[] = {
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud1", &s3c24xx_uclk),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud2", &clk_p),
|
||||
CLKDEV_INIT(NULL, "clk_uart_baud3", &clk_esys_uart.clk),
|
||||
};
|
||||
|
||||
void __init s3c2443_common_init_clocks(int xtal, pll_fn get_mpll,
|
||||
unsigned int *divs, int nr_divs,
|
||||
int divmask)
|
||||
|
@ -618,6 +626,7 @@ void __init s3c2443_common_init_clocks(int xtal, pll_fn get_mpll,
|
|||
/* See s3c2443/etc notes on disabling clocks at init time */
|
||||
s3c_register_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
s3c_disable_clocks(init_clocks_off, ARRAY_SIZE(init_clocks_off));
|
||||
clkdev_add_table(s3c2443_clk_lookup, ARRAY_SIZE(s3c2443_clk_lookup));
|
||||
|
||||
s3c2443_common_setup_clocks(get_mpll);
|
||||
}
|
||||
|
|
|
@ -18,23 +18,24 @@
|
|||
|
||||
#include <mach/dma.h>
|
||||
|
||||
static inline bool pl330_filter(struct dma_chan *chan, void *param)
|
||||
{
|
||||
struct dma_pl330_peri *peri = chan->private;
|
||||
return peri->peri_id == (unsigned)param;
|
||||
}
|
||||
|
||||
static unsigned samsung_dmadev_request(enum dma_ch dma_ch,
|
||||
struct samsung_dma_info *info)
|
||||
{
|
||||
struct dma_chan *chan;
|
||||
dma_cap_mask_t mask;
|
||||
struct dma_slave_config slave_config;
|
||||
void *filter_param;
|
||||
|
||||
dma_cap_zero(mask);
|
||||
dma_cap_set(info->cap, mask);
|
||||
|
||||
chan = dma_request_channel(mask, pl330_filter, (void *)dma_ch);
|
||||
/*
|
||||
* If a dma channel property of a device node from device tree is
|
||||
* specified, use that as the fliter parameter.
|
||||
*/
|
||||
filter_param = (dma_ch == DMACH_DT_PROP) ? (void *)info->dt_dmach_prop :
|
||||
(void *)dma_ch;
|
||||
chan = dma_request_channel(mask, pl330_filter, filter_param);
|
||||
|
||||
if (info->direction == DMA_FROM_DEVICE) {
|
||||
memset(&slave_config, 0, sizeof(struct dma_slave_config));
|
||||
|
|
|
@ -31,6 +31,7 @@ struct samsung_dma_info {
|
|||
enum dma_slave_buswidth width;
|
||||
dma_addr_t fifo;
|
||||
struct s3c2410_dma_client *client;
|
||||
struct property *dt_dmach_prop;
|
||||
};
|
||||
|
||||
struct samsung_dma_ops {
|
||||
|
|
|
@ -21,7 +21,8 @@
|
|||
* use these just as IDs.
|
||||
*/
|
||||
enum dma_ch {
|
||||
DMACH_UART0_RX,
|
||||
DMACH_DT_PROP = -1,
|
||||
DMACH_UART0_RX = 0,
|
||||
DMACH_UART0_TX,
|
||||
DMACH_UART1_RX,
|
||||
DMACH_UART1_TX,
|
||||
|
|
|
@ -44,13 +44,14 @@
|
|||
#define S5P_IRQ_VIC2(x) (S5P_VIC2_BASE + (x))
|
||||
#define S5P_IRQ_VIC3(x) (S5P_VIC3_BASE + (x))
|
||||
|
||||
#define S5P_TIMER_IRQ(x) (11 + (x))
|
||||
#define S5P_TIMER_IRQ(x) (IRQ_TIMER_BASE + (x))
|
||||
|
||||
#define IRQ_TIMER0 S5P_TIMER_IRQ(0)
|
||||
#define IRQ_TIMER1 S5P_TIMER_IRQ(1)
|
||||
#define IRQ_TIMER2 S5P_TIMER_IRQ(2)
|
||||
#define IRQ_TIMER3 S5P_TIMER_IRQ(3)
|
||||
#define IRQ_TIMER4 S5P_TIMER_IRQ(4)
|
||||
#define IRQ_TIMER_COUNT (5)
|
||||
|
||||
#define IRQ_EINT(x) ((x) < 16 ? ((x) + S5P_EINT_BASE1) \
|
||||
: ((x) - 16 + S5P_EINT_BASE2))
|
||||
|
|
|
@ -71,6 +71,7 @@
|
|||
#define S3C2410_LCON_IRM (1<<6)
|
||||
|
||||
#define S3C2440_UCON_CLKMASK (3<<10)
|
||||
#define S3C2440_UCON_CLKSHIFT (10)
|
||||
#define S3C2440_UCON_PCLK (0<<10)
|
||||
#define S3C2440_UCON_UCLK (1<<10)
|
||||
#define S3C2440_UCON_PCLK2 (2<<10)
|
||||
|
@ -78,6 +79,7 @@
|
|||
#define S3C2443_UCON_EPLL (3<<10)
|
||||
|
||||
#define S3C6400_UCON_CLKMASK (3<<10)
|
||||
#define S3C6400_UCON_CLKSHIFT (10)
|
||||
#define S3C6400_UCON_PCLK (0<<10)
|
||||
#define S3C6400_UCON_PCLK2 (2<<10)
|
||||
#define S3C6400_UCON_UCLK0 (1<<10)
|
||||
|
@ -90,11 +92,14 @@
|
|||
#define S3C2440_UCON_DIVSHIFT (12)
|
||||
|
||||
#define S3C2412_UCON_CLKMASK (3<<10)
|
||||
#define S3C2412_UCON_CLKSHIFT (10)
|
||||
#define S3C2412_UCON_UCLK (1<<10)
|
||||
#define S3C2412_UCON_USYSCLK (3<<10)
|
||||
#define S3C2412_UCON_PCLK (0<<10)
|
||||
#define S3C2412_UCON_PCLK2 (2<<10)
|
||||
|
||||
#define S3C2410_UCON_CLKMASK (1 << 10)
|
||||
#define S3C2410_UCON_CLKSHIFT (10)
|
||||
#define S3C2410_UCON_UCLK (1<<10)
|
||||
#define S3C2410_UCON_SBREAK (1<<4)
|
||||
|
||||
|
@ -193,6 +198,7 @@
|
|||
|
||||
/* Following are specific to S5PV210 */
|
||||
#define S5PV210_UCON_CLKMASK (1<<10)
|
||||
#define S5PV210_UCON_CLKSHIFT (10)
|
||||
#define S5PV210_UCON_PCLK (0<<10)
|
||||
#define S5PV210_UCON_UCLK (1<<10)
|
||||
|
||||
|
@ -221,30 +227,25 @@
|
|||
#define S5PV210_UFSTAT_RXMASK (255<<0)
|
||||
#define S5PV210_UFSTAT_RXSHIFT (0)
|
||||
|
||||
#define NO_NEED_CHECK_CLKSRC 1
|
||||
#define S3C2410_UCON_CLKSEL0 (1 << 0)
|
||||
#define S3C2410_UCON_CLKSEL1 (1 << 1)
|
||||
#define S3C2410_UCON_CLKSEL2 (1 << 2)
|
||||
#define S3C2410_UCON_CLKSEL3 (1 << 3)
|
||||
|
||||
/* Default values for s5pv210 UCON and UFCON uart registers */
|
||||
#define S5PV210_UCON_DEFAULT (S3C2410_UCON_TXILEVEL | \
|
||||
S3C2410_UCON_RXILEVEL | \
|
||||
S3C2410_UCON_TXIRQMODE | \
|
||||
S3C2410_UCON_RXIRQMODE | \
|
||||
S3C2410_UCON_RXFIFO_TOI | \
|
||||
S3C2443_UCON_RXERR_IRQEN)
|
||||
|
||||
#define S5PV210_UFCON_DEFAULT (S3C2410_UFCON_FIFOMODE | \
|
||||
S5PV210_UFCON_TXTRIG4 | \
|
||||
S5PV210_UFCON_RXTRIG4)
|
||||
|
||||
#ifndef __ASSEMBLY__
|
||||
|
||||
/* struct s3c24xx_uart_clksrc
|
||||
*
|
||||
* this structure defines a named clock source that can be used for the
|
||||
* uart, so that the best clock can be selected for the requested baud
|
||||
* rate.
|
||||
*
|
||||
* min_baud and max_baud define the range of baud-rates this clock is
|
||||
* acceptable for, if they are both zero, it is assumed any baud rate that
|
||||
* can be generated from this clock will be used.
|
||||
*
|
||||
* divisor gives the divisor from the clock to the one seen by the uart
|
||||
*/
|
||||
|
||||
struct s3c24xx_uart_clksrc {
|
||||
const char *name;
|
||||
unsigned int divisor;
|
||||
unsigned int min_baud;
|
||||
unsigned int max_baud;
|
||||
};
|
||||
|
||||
/* configuration structure for per-machine configurations for the
|
||||
* serial port
|
||||
*
|
||||
|
@ -257,15 +258,13 @@ struct s3c2410_uartcfg {
|
|||
unsigned char unused;
|
||||
unsigned short flags;
|
||||
upf_t uart_flags; /* default uart flags */
|
||||
unsigned int clk_sel;
|
||||
|
||||
unsigned int has_fracval;
|
||||
|
||||
unsigned long ucon; /* value of ucon for port */
|
||||
unsigned long ulcon; /* value of ulcon for port */
|
||||
unsigned long ufcon; /* value of ufcon for port */
|
||||
|
||||
struct s3c24xx_uart_clksrc *clocks;
|
||||
unsigned int clocks_size;
|
||||
};
|
||||
|
||||
/* s3c24xx_uart_devs
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
#include <linux/amba/pl330.h>
|
||||
#include <linux/pm_runtime.h>
|
||||
#include <linux/scatterlist.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
#define NR_DEFAULT_DESC 16
|
||||
|
||||
|
@ -116,6 +117,9 @@ struct dma_pl330_desc {
|
|||
struct dma_pl330_chan *pchan;
|
||||
};
|
||||
|
||||
/* forward declaration */
|
||||
static struct amba_driver pl330_driver;
|
||||
|
||||
static inline struct dma_pl330_chan *
|
||||
to_pchan(struct dma_chan *ch)
|
||||
{
|
||||
|
@ -267,6 +271,32 @@ static void dma_pl330_rqcb(void *token, enum pl330_op_err err)
|
|||
tasklet_schedule(&pch->task);
|
||||
}
|
||||
|
||||
bool pl330_filter(struct dma_chan *chan, void *param)
|
||||
{
|
||||
u8 *peri_id;
|
||||
|
||||
if (chan->device->dev->driver != &pl330_driver.drv)
|
||||
return false;
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
if (chan->device->dev->of_node) {
|
||||
const __be32 *prop_value;
|
||||
phandle phandle;
|
||||
struct device_node *node;
|
||||
|
||||
prop_value = ((struct property *)param)->value;
|
||||
phandle = be32_to_cpup(prop_value++);
|
||||
node = of_find_node_by_phandle(phandle);
|
||||
return ((chan->private == node) &&
|
||||
(chan->chan_id == be32_to_cpup(prop_value)));
|
||||
}
|
||||
#endif
|
||||
|
||||
peri_id = chan->private;
|
||||
return *peri_id == (unsigned)param;
|
||||
}
|
||||
EXPORT_SYMBOL(pl330_filter);
|
||||
|
||||
static int pl330_alloc_chan_resources(struct dma_chan *chan)
|
||||
{
|
||||
struct dma_pl330_chan *pch = to_pchan(chan);
|
||||
|
@ -497,7 +527,7 @@ pluck_desc(struct dma_pl330_dmac *pdmac)
|
|||
static struct dma_pl330_desc *pl330_get_desc(struct dma_pl330_chan *pch)
|
||||
{
|
||||
struct dma_pl330_dmac *pdmac = pch->dmac;
|
||||
struct dma_pl330_peri *peri = pch->chan.private;
|
||||
u8 *peri_id = pch->chan.private;
|
||||
struct dma_pl330_desc *desc;
|
||||
|
||||
/* Pluck one desc from the pool of DMAC */
|
||||
|
@ -522,13 +552,7 @@ static struct dma_pl330_desc *pl330_get_desc(struct dma_pl330_chan *pch)
|
|||
desc->txd.cookie = 0;
|
||||
async_tx_ack(&desc->txd);
|
||||
|
||||
if (peri) {
|
||||
desc->req.rqtype = peri->rqtype;
|
||||
desc->req.peri = pch->chan.chan_id;
|
||||
} else {
|
||||
desc->req.rqtype = MEMTOMEM;
|
||||
desc->req.peri = 0;
|
||||
}
|
||||
desc->req.peri = peri_id ? pch->chan.chan_id : 0;
|
||||
|
||||
dma_async_tx_descriptor_init(&desc->txd, &pch->chan);
|
||||
|
||||
|
@ -615,12 +639,14 @@ static struct dma_async_tx_descriptor *pl330_prep_dma_cyclic(
|
|||
case DMA_TO_DEVICE:
|
||||
desc->rqcfg.src_inc = 1;
|
||||
desc->rqcfg.dst_inc = 0;
|
||||
desc->req.rqtype = MEMTODEV;
|
||||
src = dma_addr;
|
||||
dst = pch->fifo_addr;
|
||||
break;
|
||||
case DMA_FROM_DEVICE:
|
||||
desc->rqcfg.src_inc = 0;
|
||||
desc->rqcfg.dst_inc = 1;
|
||||
desc->req.rqtype = DEVTOMEM;
|
||||
src = pch->fifo_addr;
|
||||
dst = dma_addr;
|
||||
break;
|
||||
|
@ -646,16 +672,12 @@ pl330_prep_dma_memcpy(struct dma_chan *chan, dma_addr_t dst,
|
|||
{
|
||||
struct dma_pl330_desc *desc;
|
||||
struct dma_pl330_chan *pch = to_pchan(chan);
|
||||
struct dma_pl330_peri *peri = chan->private;
|
||||
struct pl330_info *pi;
|
||||
int burst;
|
||||
|
||||
if (unlikely(!pch || !len))
|
||||
return NULL;
|
||||
|
||||
if (peri && peri->rqtype != MEMTOMEM)
|
||||
return NULL;
|
||||
|
||||
pi = &pch->dmac->pif;
|
||||
|
||||
desc = __pl330_prep_dma_memcpy(pch, dst, src, len);
|
||||
|
@ -664,6 +686,7 @@ pl330_prep_dma_memcpy(struct dma_chan *chan, dma_addr_t dst,
|
|||
|
||||
desc->rqcfg.src_inc = 1;
|
||||
desc->rqcfg.dst_inc = 1;
|
||||
desc->req.rqtype = MEMTOMEM;
|
||||
|
||||
/* Select max possible burst size */
|
||||
burst = pi->pcfg.data_bus_width / 8;
|
||||
|
@ -692,25 +715,14 @@ pl330_prep_slave_sg(struct dma_chan *chan, struct scatterlist *sgl,
|
|||
{
|
||||
struct dma_pl330_desc *first, *desc = NULL;
|
||||
struct dma_pl330_chan *pch = to_pchan(chan);
|
||||
struct dma_pl330_peri *peri = chan->private;
|
||||
struct scatterlist *sg;
|
||||
unsigned long flags;
|
||||
int i;
|
||||
dma_addr_t addr;
|
||||
|
||||
if (unlikely(!pch || !sgl || !sg_len || !peri))
|
||||
if (unlikely(!pch || !sgl || !sg_len))
|
||||
return NULL;
|
||||
|
||||
/* Make sure the direction is consistent */
|
||||
if ((direction == DMA_TO_DEVICE &&
|
||||
peri->rqtype != MEMTODEV) ||
|
||||
(direction == DMA_FROM_DEVICE &&
|
||||
peri->rqtype != DEVTOMEM)) {
|
||||
dev_err(pch->dmac->pif.dev, "%s:%d Invalid Direction\n",
|
||||
__func__, __LINE__);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
addr = pch->fifo_addr;
|
||||
|
||||
first = NULL;
|
||||
|
@ -750,11 +762,13 @@ pl330_prep_slave_sg(struct dma_chan *chan, struct scatterlist *sgl,
|
|||
if (direction == DMA_TO_DEVICE) {
|
||||
desc->rqcfg.src_inc = 1;
|
||||
desc->rqcfg.dst_inc = 0;
|
||||
desc->req.rqtype = MEMTODEV;
|
||||
fill_px(&desc->px,
|
||||
addr, sg_dma_address(sg), sg_dma_len(sg));
|
||||
} else {
|
||||
desc->rqcfg.src_inc = 0;
|
||||
desc->rqcfg.dst_inc = 1;
|
||||
desc->req.rqtype = DEVTOMEM;
|
||||
fill_px(&desc->px,
|
||||
sg_dma_address(sg), addr, sg_dma_len(sg));
|
||||
}
|
||||
|
@ -856,32 +870,16 @@ pl330_probe(struct amba_device *adev, const struct amba_id *id)
|
|||
INIT_LIST_HEAD(&pd->channels);
|
||||
|
||||
/* Initialize channel parameters */
|
||||
num_chan = max(pdat ? pdat->nr_valid_peri : 0, (u8)pi->pcfg.num_chan);
|
||||
num_chan = max(pdat ? pdat->nr_valid_peri : (u8)pi->pcfg.num_peri,
|
||||
(u8)pi->pcfg.num_chan);
|
||||
pdmac->peripherals = kzalloc(num_chan * sizeof(*pch), GFP_KERNEL);
|
||||
|
||||
for (i = 0; i < num_chan; i++) {
|
||||
pch = &pdmac->peripherals[i];
|
||||
if (pdat) {
|
||||
struct dma_pl330_peri *peri = &pdat->peri[i];
|
||||
|
||||
switch (peri->rqtype) {
|
||||
case MEMTOMEM:
|
||||
dma_cap_set(DMA_MEMCPY, pd->cap_mask);
|
||||
break;
|
||||
case MEMTODEV:
|
||||
case DEVTOMEM:
|
||||
dma_cap_set(DMA_SLAVE, pd->cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, pd->cap_mask);
|
||||
break;
|
||||
default:
|
||||
dev_err(&adev->dev, "DEVTODEV Not Supported\n");
|
||||
continue;
|
||||
}
|
||||
pch->chan.private = peri;
|
||||
} else {
|
||||
dma_cap_set(DMA_MEMCPY, pd->cap_mask);
|
||||
pch->chan.private = NULL;
|
||||
}
|
||||
if (!adev->dev.of_node)
|
||||
pch->chan.private = pdat ? &pdat->peri_id[i] : NULL;
|
||||
else
|
||||
pch->chan.private = adev->dev.of_node;
|
||||
|
||||
INIT_LIST_HEAD(&pch->work_list);
|
||||
spin_lock_init(&pch->lock);
|
||||
|
@ -894,6 +892,15 @@ pl330_probe(struct amba_device *adev, const struct amba_id *id)
|
|||
}
|
||||
|
||||
pd->dev = &adev->dev;
|
||||
if (pdat) {
|
||||
pd->cap_mask = pdat->cap_mask;
|
||||
} else {
|
||||
dma_cap_set(DMA_MEMCPY, pd->cap_mask);
|
||||
if (pi->pcfg.num_peri) {
|
||||
dma_cap_set(DMA_SLAVE, pd->cap_mask);
|
||||
dma_cap_set(DMA_CYCLIC, pd->cap_mask);
|
||||
}
|
||||
}
|
||||
|
||||
pd->device_alloc_chan_resources = pl330_alloc_chan_resources;
|
||||
pd->device_free_chan_resources = pl330_free_chan_resources;
|
||||
|
|
|
@ -24,6 +24,9 @@
|
|||
#include <linux/interrupt.h>
|
||||
#include <linux/sysdev.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/of.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/of_address.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
|
||||
|
@ -2374,6 +2377,63 @@ static struct samsung_gpio_chip exynos4_gpios_3[] = {
|
|||
#endif
|
||||
};
|
||||
|
||||
#if defined(CONFIG_ARCH_EXYNOS4) && defined(CONFIG_OF)
|
||||
static int exynos4_gpio_xlate(struct gpio_chip *gc, struct device_node *np,
|
||||
const void *gpio_spec, u32 *flags)
|
||||
{
|
||||
const __be32 *gpio = gpio_spec;
|
||||
const u32 n = be32_to_cpup(gpio);
|
||||
unsigned int pin = gc->base + be32_to_cpu(gpio[0]);
|
||||
|
||||
if (WARN_ON(gc->of_gpio_n_cells < 4))
|
||||
return -EINVAL;
|
||||
|
||||
if (n > gc->ngpio)
|
||||
return -EINVAL;
|
||||
|
||||
if (s3c_gpio_cfgpin(pin, S3C_GPIO_SFN(be32_to_cpu(gpio[1]))))
|
||||
pr_warn("gpio_xlate: failed to set pin function\n");
|
||||
if (s3c_gpio_setpull(pin, be32_to_cpu(gpio[2])))
|
||||
pr_warn("gpio_xlate: failed to set pin pull up/down\n");
|
||||
if (s5p_gpio_set_drvstr(pin, be32_to_cpu(gpio[3])))
|
||||
pr_warn("gpio_xlate: failed to set pin drive strength\n");
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
static const struct of_device_id exynos4_gpio_dt_match[] __initdata = {
|
||||
{ .compatible = "samsung,exynos4-gpio", },
|
||||
{}
|
||||
};
|
||||
|
||||
static __init void exynos4_gpiolib_attach_ofnode(struct samsung_gpio_chip *chip,
|
||||
u64 base, u64 offset)
|
||||
{
|
||||
struct gpio_chip *gc = &chip->chip;
|
||||
u64 address;
|
||||
|
||||
if (!of_have_populated_dt())
|
||||
return;
|
||||
|
||||
address = chip->base ? base + ((u32)chip->base & 0xfff) : base + offset;
|
||||
gc->of_node = of_find_matching_node_by_address(NULL,
|
||||
exynos4_gpio_dt_match, address);
|
||||
if (!gc->of_node) {
|
||||
pr_info("gpio: device tree node not found for gpio controller"
|
||||
" with base address %08llx\n", address);
|
||||
return;
|
||||
}
|
||||
gc->of_gpio_n_cells = 4;
|
||||
gc->of_xlate = exynos4_gpio_xlate;
|
||||
}
|
||||
#elif defined(CONFIG_ARCH_EXYNOS4)
|
||||
static __init void exynos4_gpiolib_attach_ofnode(struct samsung_gpio_chip *chip,
|
||||
u64 base, u64 offset)
|
||||
{
|
||||
return;
|
||||
}
|
||||
#endif /* defined(CONFIG_ARCH_EXYNOS4) && defined(CONFIG_OF) */
|
||||
|
||||
/* TODO: cleanup soc_is_* */
|
||||
static __init int samsung_gpiolib_init(void)
|
||||
{
|
||||
|
@ -2455,6 +2515,10 @@ static __init int samsung_gpiolib_init(void)
|
|||
chip->config = &exynos4_gpio_cfg;
|
||||
chip->group = group++;
|
||||
}
|
||||
#ifdef CONFIG_CPU_EXYNOS4210
|
||||
exynos4_gpiolib_attach_ofnode(chip,
|
||||
EXYNOS4_PA_GPIO1, i * 0x20);
|
||||
#endif
|
||||
}
|
||||
samsung_gpiolib_add_4bit_chips(exynos4_gpios_1, nr_chips, S5P_VA_GPIO1);
|
||||
|
||||
|
@ -2467,6 +2531,10 @@ static __init int samsung_gpiolib_init(void)
|
|||
chip->config = &exynos4_gpio_cfg;
|
||||
chip->group = group++;
|
||||
}
|
||||
#ifdef CONFIG_CPU_EXYNOS4210
|
||||
exynos4_gpiolib_attach_ofnode(chip,
|
||||
EXYNOS4_PA_GPIO2, i * 0x20);
|
||||
#endif
|
||||
}
|
||||
samsung_gpiolib_add_4bit_chips(exynos4_gpios_2, nr_chips, S5P_VA_GPIO2);
|
||||
|
||||
|
@ -2479,6 +2547,10 @@ static __init int samsung_gpiolib_init(void)
|
|||
chip->config = &exynos4_gpio_cfg;
|
||||
chip->group = group++;
|
||||
}
|
||||
#ifdef CONFIG_CPU_EXYNOS4210
|
||||
exynos4_gpiolib_attach_ofnode(chip,
|
||||
EXYNOS4_PA_GPIO3, i * 0x20);
|
||||
#endif
|
||||
}
|
||||
samsung_gpiolib_add_4bit_chips(exynos4_gpios_3, nr_chips, S5P_VA_GPIO3);
|
||||
|
||||
|
|
|
@ -21,6 +21,8 @@
|
|||
#include <linux/module.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/of.h>
|
||||
#include <linux/of_gpio.h>
|
||||
#include <linux/sched.h>
|
||||
#include <plat/keypad.h>
|
||||
|
||||
|
@ -68,31 +70,26 @@ struct samsung_keypad {
|
|||
wait_queue_head_t wait;
|
||||
bool stopped;
|
||||
int irq;
|
||||
enum samsung_keypad_type type;
|
||||
unsigned int row_shift;
|
||||
unsigned int rows;
|
||||
unsigned int cols;
|
||||
unsigned int row_state[SAMSUNG_MAX_COLS];
|
||||
#ifdef CONFIG_OF
|
||||
int row_gpios[SAMSUNG_MAX_ROWS];
|
||||
int col_gpios[SAMSUNG_MAX_COLS];
|
||||
#endif
|
||||
unsigned short keycodes[];
|
||||
};
|
||||
|
||||
static int samsung_keypad_is_s5pv210(struct device *dev)
|
||||
{
|
||||
struct platform_device *pdev = to_platform_device(dev);
|
||||
enum samsung_keypad_type type =
|
||||
platform_get_device_id(pdev)->driver_data;
|
||||
|
||||
return type == KEYPAD_TYPE_S5PV210;
|
||||
}
|
||||
|
||||
static void samsung_keypad_scan(struct samsung_keypad *keypad,
|
||||
unsigned int *row_state)
|
||||
{
|
||||
struct device *dev = keypad->input_dev->dev.parent;
|
||||
unsigned int col;
|
||||
unsigned int val;
|
||||
|
||||
for (col = 0; col < keypad->cols; col++) {
|
||||
if (samsung_keypad_is_s5pv210(dev)) {
|
||||
if (keypad->type == KEYPAD_TYPE_S5PV210) {
|
||||
val = S5PV210_KEYIFCOLEN_MASK;
|
||||
val &= ~(1 << col) << 8;
|
||||
} else {
|
||||
|
@ -235,6 +232,126 @@ static void samsung_keypad_close(struct input_dev *input_dev)
|
|||
samsung_keypad_stop(keypad);
|
||||
}
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static struct samsung_keypad_platdata *samsung_keypad_parse_dt(
|
||||
struct device *dev)
|
||||
{
|
||||
struct samsung_keypad_platdata *pdata;
|
||||
struct matrix_keymap_data *keymap_data;
|
||||
uint32_t *keymap, num_rows = 0, num_cols = 0;
|
||||
struct device_node *np = dev->of_node, *key_np;
|
||||
unsigned int key_count = 0;
|
||||
|
||||
pdata = devm_kzalloc(dev, sizeof(*pdata), GFP_KERNEL);
|
||||
if (!pdata) {
|
||||
dev_err(dev, "could not allocate memory for platform data\n");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
of_property_read_u32(np, "samsung,keypad-num-rows", &num_rows);
|
||||
of_property_read_u32(np, "samsung,keypad-num-columns", &num_cols);
|
||||
if (!num_rows || !num_cols) {
|
||||
dev_err(dev, "number of keypad rows/columns not specified\n");
|
||||
return NULL;
|
||||
}
|
||||
pdata->rows = num_rows;
|
||||
pdata->cols = num_cols;
|
||||
|
||||
keymap_data = devm_kzalloc(dev, sizeof(*keymap_data), GFP_KERNEL);
|
||||
if (!keymap_data) {
|
||||
dev_err(dev, "could not allocate memory for keymap data\n");
|
||||
return NULL;
|
||||
}
|
||||
pdata->keymap_data = keymap_data;
|
||||
|
||||
for_each_child_of_node(np, key_np)
|
||||
key_count++;
|
||||
|
||||
keymap_data->keymap_size = key_count;
|
||||
keymap = devm_kzalloc(dev, sizeof(uint32_t) * key_count, GFP_KERNEL);
|
||||
if (!keymap) {
|
||||
dev_err(dev, "could not allocate memory for keymap\n");
|
||||
return NULL;
|
||||
}
|
||||
keymap_data->keymap = keymap;
|
||||
|
||||
for_each_child_of_node(np, key_np) {
|
||||
u32 row, col, key_code;
|
||||
of_property_read_u32(key_np, "keypad,row", &row);
|
||||
of_property_read_u32(key_np, "keypad,column", &col);
|
||||
of_property_read_u32(key_np, "linux,code", &key_code);
|
||||
*keymap++ = KEY(row, col, key_code);
|
||||
}
|
||||
|
||||
if (of_get_property(np, "linux,input-no-autorepeat", NULL))
|
||||
pdata->no_autorepeat = true;
|
||||
if (of_get_property(np, "linux,input-wakeup", NULL))
|
||||
pdata->wakeup = true;
|
||||
|
||||
return pdata;
|
||||
}
|
||||
|
||||
static void samsung_keypad_parse_dt_gpio(struct device *dev,
|
||||
struct samsung_keypad *keypad)
|
||||
{
|
||||
struct device_node *np = dev->of_node;
|
||||
int gpio, ret, row, col;
|
||||
|
||||
for (row = 0; row < keypad->rows; row++) {
|
||||
gpio = of_get_named_gpio(np, "row-gpios", row);
|
||||
keypad->row_gpios[row] = gpio;
|
||||
if (!gpio_is_valid(gpio)) {
|
||||
dev_err(dev, "keypad row[%d]: invalid gpio %d\n",
|
||||
row, gpio);
|
||||
continue;
|
||||
}
|
||||
|
||||
ret = gpio_request(gpio, "keypad-row");
|
||||
if (ret)
|
||||
dev_err(dev, "keypad row[%d] gpio request failed\n",
|
||||
row);
|
||||
}
|
||||
|
||||
for (col = 0; col < keypad->cols; col++) {
|
||||
gpio = of_get_named_gpio(np, "col-gpios", col);
|
||||
keypad->col_gpios[col] = gpio;
|
||||
if (!gpio_is_valid(gpio)) {
|
||||
dev_err(dev, "keypad column[%d]: invalid gpio %d\n",
|
||||
col, gpio);
|
||||
continue;
|
||||
}
|
||||
|
||||
ret = gpio_request(gpio, "keypad-col");
|
||||
if (ret)
|
||||
dev_err(dev, "keypad column[%d] gpio request failed\n",
|
||||
col);
|
||||
}
|
||||
}
|
||||
|
||||
static void samsung_keypad_dt_gpio_free(struct samsung_keypad *keypad)
|
||||
{
|
||||
int cnt;
|
||||
|
||||
for (cnt = 0; cnt < keypad->rows; cnt++)
|
||||
if (gpio_is_valid(keypad->row_gpios[cnt]))
|
||||
gpio_free(keypad->row_gpios[cnt]);
|
||||
|
||||
for (cnt = 0; cnt < keypad->cols; cnt++)
|
||||
if (gpio_is_valid(keypad->col_gpios[cnt]))
|
||||
gpio_free(keypad->col_gpios[cnt]);
|
||||
}
|
||||
#else
|
||||
static
|
||||
struct samsung_keypad_platdata *samsung_keypad_parse_dt(struct device *dev)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static void samsung_keypad_dt_gpio_free(struct samsung_keypad *keypad)
|
||||
{
|
||||
}
|
||||
#endif
|
||||
|
||||
static int __devinit samsung_keypad_probe(struct platform_device *pdev)
|
||||
{
|
||||
const struct samsung_keypad_platdata *pdata;
|
||||
|
@ -246,7 +363,10 @@ static int __devinit samsung_keypad_probe(struct platform_device *pdev)
|
|||
unsigned int keymap_size;
|
||||
int error;
|
||||
|
||||
pdata = pdev->dev.platform_data;
|
||||
if (pdev->dev.of_node)
|
||||
pdata = samsung_keypad_parse_dt(&pdev->dev);
|
||||
else
|
||||
pdata = pdev->dev.platform_data;
|
||||
if (!pdata) {
|
||||
dev_err(&pdev->dev, "no platform data defined\n");
|
||||
return -EINVAL;
|
||||
|
@ -303,6 +423,16 @@ static int __devinit samsung_keypad_probe(struct platform_device *pdev)
|
|||
keypad->cols = pdata->cols;
|
||||
init_waitqueue_head(&keypad->wait);
|
||||
|
||||
if (pdev->dev.of_node) {
|
||||
#ifdef CONFIG_OF
|
||||
samsung_keypad_parse_dt_gpio(&pdev->dev, keypad);
|
||||
keypad->type = of_device_is_compatible(pdev->dev.of_node,
|
||||
"samsung,s5pv210-keypad");
|
||||
#endif
|
||||
} else {
|
||||
keypad->type = platform_get_device_id(pdev)->driver_data;
|
||||
}
|
||||
|
||||
input_dev->name = pdev->name;
|
||||
input_dev->id.bustype = BUS_HOST;
|
||||
input_dev->dev.parent = &pdev->dev;
|
||||
|
@ -343,12 +473,19 @@ static int __devinit samsung_keypad_probe(struct platform_device *pdev)
|
|||
|
||||
device_init_wakeup(&pdev->dev, pdata->wakeup);
|
||||
platform_set_drvdata(pdev, keypad);
|
||||
|
||||
if (pdev->dev.of_node) {
|
||||
devm_kfree(&pdev->dev, (void *)pdata->keymap_data->keymap);
|
||||
devm_kfree(&pdev->dev, (void *)pdata->keymap_data);
|
||||
devm_kfree(&pdev->dev, (void *)pdata);
|
||||
}
|
||||
return 0;
|
||||
|
||||
err_free_irq:
|
||||
free_irq(keypad->irq, keypad);
|
||||
err_put_clk:
|
||||
clk_put(keypad->clk);
|
||||
samsung_keypad_dt_gpio_free(keypad);
|
||||
err_unmap_base:
|
||||
iounmap(keypad->base);
|
||||
err_free_mem:
|
||||
|
@ -374,6 +511,7 @@ static int __devexit samsung_keypad_remove(struct platform_device *pdev)
|
|||
free_irq(keypad->irq, keypad);
|
||||
|
||||
clk_put(keypad->clk);
|
||||
samsung_keypad_dt_gpio_free(keypad);
|
||||
|
||||
iounmap(keypad->base);
|
||||
kfree(keypad);
|
||||
|
@ -447,6 +585,17 @@ static const struct dev_pm_ops samsung_keypad_pm_ops = {
|
|||
};
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static const struct of_device_id samsung_keypad_dt_match[] = {
|
||||
{ .compatible = "samsung,s3c6410-keypad" },
|
||||
{ .compatible = "samsung,s5pv210-keypad" },
|
||||
{},
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, samsung_keypad_dt_match);
|
||||
#else
|
||||
#define samsung_keypad_dt_match NULL
|
||||
#endif
|
||||
|
||||
static struct platform_device_id samsung_keypad_driver_ids[] = {
|
||||
{
|
||||
.name = "samsung-keypad",
|
||||
|
@ -465,6 +614,7 @@ static struct platform_driver samsung_keypad_driver = {
|
|||
.driver = {
|
||||
.name = "samsung-keypad",
|
||||
.owner = THIS_MODULE,
|
||||
.of_match_table = samsung_keypad_dt_match,
|
||||
#ifdef CONFIG_PM
|
||||
.pm = &samsung_keypad_pm_ops,
|
||||
#endif
|
||||
|
|
|
@ -25,6 +25,7 @@
|
|||
#include <linux/clk.h>
|
||||
#include <linux/log2.h>
|
||||
#include <linux/slab.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
#include <mach/hardware.h>
|
||||
#include <asm/uaccess.h>
|
||||
|
@ -507,7 +508,13 @@ static int __devinit s3c_rtc_probe(struct platform_device *pdev)
|
|||
goto err_nortc;
|
||||
}
|
||||
|
||||
s3c_rtc_cpu_type = platform_get_device_id(pdev)->driver_data;
|
||||
#ifdef CONFIG_OF
|
||||
if (pdev->dev.of_node)
|
||||
s3c_rtc_cpu_type = of_device_is_compatible(pdev->dev.of_node,
|
||||
"samsung,s3c6410-rtc") ? TYPE_S3C64XX : TYPE_S3C2410;
|
||||
else
|
||||
#endif
|
||||
s3c_rtc_cpu_type = platform_get_device_id(pdev)->driver_data;
|
||||
|
||||
/* Check RTC Time */
|
||||
|
||||
|
@ -629,6 +636,17 @@ static int s3c_rtc_resume(struct platform_device *pdev)
|
|||
#define s3c_rtc_resume NULL
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static const struct of_device_id s3c_rtc_dt_match[] = {
|
||||
{ .compatible = "samsung,s3c2410-rtc" },
|
||||
{ .compatible = "samsung,s3c6410-rtc" },
|
||||
{},
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, s3c_rtc_dt_match);
|
||||
#else
|
||||
#define s3c_rtc_dt_match NULL
|
||||
#endif
|
||||
|
||||
static struct platform_device_id s3c_rtc_driver_ids[] = {
|
||||
{
|
||||
.name = "s3c2410-rtc",
|
||||
|
@ -651,6 +669,7 @@ static struct platform_driver s3c_rtc_driver = {
|
|||
.driver = {
|
||||
.name = "s3c-rtc",
|
||||
.owner = THIS_MODULE,
|
||||
.of_match_table = s3c_rtc_dt_match,
|
||||
},
|
||||
};
|
||||
|
||||
|
|
|
@ -457,7 +457,7 @@ config SERIAL_SAMSUNG
|
|||
config SERIAL_SAMSUNG_UARTS_4
|
||||
bool
|
||||
depends on ARM && PLAT_SAMSUNG
|
||||
default y if CPU_S3C2443
|
||||
default y if !(CPU_S3C2410 || SERIAL_S3C2412 || CPU_S3C2440 || CPU_S3C2442)
|
||||
help
|
||||
Internal node for the common case of 4 Samsung compatible UARTs
|
||||
|
||||
|
@ -465,7 +465,7 @@ config SERIAL_SAMSUNG_UARTS
|
|||
int
|
||||
depends on ARM && PLAT_SAMSUNG
|
||||
default 6 if ARCH_S5P6450
|
||||
default 4 if SERIAL_SAMSUNG_UARTS_4
|
||||
default 4 if SERIAL_SAMSUNG_UARTS_4 || CPU_S3C2416
|
||||
default 3
|
||||
help
|
||||
Select the number of available UART ports for the Samsung S3C
|
||||
|
@ -495,47 +495,6 @@ config SERIAL_SAMSUNG_CONSOLE
|
|||
your boot loader about how to pass options to the kernel at
|
||||
boot time.)
|
||||
|
||||
config SERIAL_S3C2410
|
||||
tristate "Samsung S3C2410 Serial port support"
|
||||
depends on SERIAL_SAMSUNG && CPU_S3C2410
|
||||
default y if CPU_S3C2410
|
||||
help
|
||||
Serial port support for the Samsung S3C2410 SoC
|
||||
|
||||
config SERIAL_S3C2412
|
||||
tristate "Samsung S3C2412/S3C2413 Serial port support"
|
||||
depends on SERIAL_SAMSUNG && CPU_S3C2412
|
||||
default y if CPU_S3C2412
|
||||
help
|
||||
Serial port support for the Samsung S3C2412 and S3C2413 SoC
|
||||
|
||||
config SERIAL_S3C2440
|
||||
tristate "Samsung S3C2440/S3C2442/S3C2416 Serial port support"
|
||||
depends on SERIAL_SAMSUNG && (CPU_S3C2440 || CPU_S3C2442 || CPU_S3C2416)
|
||||
default y if CPU_S3C2440
|
||||
default y if CPU_S3C2442
|
||||
select SERIAL_SAMSUNG_UARTS_4 if CPU_S3C2416
|
||||
help
|
||||
Serial port support for the Samsung S3C2440, S3C2416 and S3C2442 SoC
|
||||
|
||||
config SERIAL_S3C6400
|
||||
tristate "Samsung S3C6400/S3C6410/S5P6440/S5P6450/S5PC100 Serial port support"
|
||||
depends on SERIAL_SAMSUNG && (CPU_S3C6400 || CPU_S3C6410 || CPU_S5P6440 || CPU_S5P6450 || CPU_S5PC100)
|
||||
select SERIAL_SAMSUNG_UARTS_4
|
||||
default y
|
||||
help
|
||||
Serial port support for the Samsung S3C6400, S3C6410, S5P6440, S5P6450
|
||||
and S5PC100 SoCs
|
||||
|
||||
config SERIAL_S5PV210
|
||||
tristate "Samsung S5PV210 Serial port support"
|
||||
depends on SERIAL_SAMSUNG && (CPU_S5PV210 || CPU_EXYNOS4210 || SOC_EXYNOS4212)
|
||||
select SERIAL_SAMSUNG_UARTS_4 if (CPU_S5PV210 || CPU_EXYNOS4210 || SOC_EXYNOS4212)
|
||||
default y
|
||||
help
|
||||
Serial port support for Samsung's S5P Family of SoC's
|
||||
|
||||
|
||||
config SERIAL_MAX3100
|
||||
tristate "MAX3100 support"
|
||||
depends on SPI
|
||||
|
|
|
@ -39,11 +39,6 @@ obj-$(CONFIG_SERIAL_BCM63XX) += bcm63xx_uart.o
|
|||
obj-$(CONFIG_SERIAL_BFIN) += bfin_uart.o
|
||||
obj-$(CONFIG_SERIAL_BFIN_SPORT) += bfin_sport_uart.o
|
||||
obj-$(CONFIG_SERIAL_SAMSUNG) += samsung.o
|
||||
obj-$(CONFIG_SERIAL_S3C2410) += s3c2410.o
|
||||
obj-$(CONFIG_SERIAL_S3C2412) += s3c2412.o
|
||||
obj-$(CONFIG_SERIAL_S3C2440) += s3c2440.o
|
||||
obj-$(CONFIG_SERIAL_S3C6400) += s3c6400.o
|
||||
obj-$(CONFIG_SERIAL_S5PV210) += s5pv210.o
|
||||
obj-$(CONFIG_SERIAL_MAX3100) += max3100.o
|
||||
obj-$(CONFIG_SERIAL_MAX3107) += max3107.o
|
||||
obj-$(CONFIG_SERIAL_MAX3107_AAVA) += max3107-aava.o
|
||||
|
|
|
@ -1,115 +0,0 @@
|
|||
/*
|
||||
* Driver for Samsung S3C2410 SoC onboard UARTs.
|
||||
*
|
||||
* Ben Dooks, Copyright (c) 2003-2008 Simtec Electronics
|
||||
* http://armlinux.simtec.co.uk/
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#include <linux/module.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/serial_core.h>
|
||||
#include <linux/serial.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
#include <mach/hardware.h>
|
||||
|
||||
#include <plat/regs-serial.h>
|
||||
#include <mach/regs-gpio.h>
|
||||
|
||||
#include "samsung.h"
|
||||
|
||||
static int s3c2410_serial_setsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
if (strcmp(clk->name, "uclk") == 0)
|
||||
ucon |= S3C2410_UCON_UCLK;
|
||||
else
|
||||
ucon &= ~S3C2410_UCON_UCLK;
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int s3c2410_serial_getsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
clk->divisor = 1;
|
||||
clk->name = (ucon & S3C2410_UCON_UCLK) ? "uclk" : "pclk";
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int s3c2410_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
{
|
||||
dbg("s3c2410_serial_resetport: port=%p (%08lx), cfg=%p\n",
|
||||
port, port->mapbase, cfg);
|
||||
|
||||
wr_regl(port, S3C2410_UCON, cfg->ucon);
|
||||
wr_regl(port, S3C2410_ULCON, cfg->ulcon);
|
||||
|
||||
/* reset both fifos */
|
||||
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon | S3C2410_UFCON_RESETBOTH);
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct s3c24xx_uart_info s3c2410_uart_inf = {
|
||||
.name = "Samsung S3C2410 UART",
|
||||
.type = PORT_S3C2410,
|
||||
.fifosize = 16,
|
||||
.rx_fifomask = S3C2410_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2410_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2410_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2410_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2410_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2410_UFSTAT_TXSHIFT,
|
||||
.get_clksrc = s3c2410_serial_getsource,
|
||||
.set_clksrc = s3c2410_serial_setsource,
|
||||
.reset_port = s3c2410_serial_resetport,
|
||||
};
|
||||
|
||||
static int s3c2410_serial_probe(struct platform_device *dev)
|
||||
{
|
||||
return s3c24xx_serial_probe(dev, &s3c2410_uart_inf);
|
||||
}
|
||||
|
||||
static struct platform_driver s3c2410_serial_driver = {
|
||||
.probe = s3c2410_serial_probe,
|
||||
.remove = __devexit_p(s3c24xx_serial_remove),
|
||||
.driver = {
|
||||
.name = "s3c2410-uart",
|
||||
.owner = THIS_MODULE,
|
||||
},
|
||||
};
|
||||
|
||||
static int __init s3c2410_serial_init(void)
|
||||
{
|
||||
return s3c24xx_serial_init(&s3c2410_serial_driver, &s3c2410_uart_inf);
|
||||
}
|
||||
|
||||
static void __exit s3c2410_serial_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&s3c2410_serial_driver);
|
||||
}
|
||||
|
||||
module_init(s3c2410_serial_init);
|
||||
module_exit(s3c2410_serial_exit);
|
||||
|
||||
MODULE_LICENSE("GPL v2");
|
||||
MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>");
|
||||
MODULE_DESCRIPTION("Samsung S3C2410 SoC Serial port driver");
|
||||
MODULE_ALIAS("platform:s3c2410-uart");
|
|
@ -1,149 +0,0 @@
|
|||
/*
|
||||
* Driver for Samsung S3C2412 and S3C2413 SoC onboard UARTs.
|
||||
*
|
||||
* Ben Dooks, Copyright (c) 2003-2008 Simtec Electronics
|
||||
* http://armlinux.simtec.co.uk/
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#include <linux/module.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/serial_core.h>
|
||||
#include <linux/serial.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
#include <mach/hardware.h>
|
||||
|
||||
#include <plat/regs-serial.h>
|
||||
#include <mach/regs-gpio.h>
|
||||
|
||||
#include "samsung.h"
|
||||
|
||||
static int s3c2412_serial_setsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
ucon &= ~S3C2412_UCON_CLKMASK;
|
||||
|
||||
if (strcmp(clk->name, "uclk") == 0)
|
||||
ucon |= S3C2440_UCON_UCLK;
|
||||
else if (strcmp(clk->name, "pclk") == 0)
|
||||
ucon |= S3C2440_UCON_PCLK;
|
||||
else if (strcmp(clk->name, "usysclk") == 0)
|
||||
ucon |= S3C2412_UCON_USYSCLK;
|
||||
else {
|
||||
printk(KERN_ERR "unknown clock source %s\n", clk->name);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int s3c2412_serial_getsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
switch (ucon & S3C2412_UCON_CLKMASK) {
|
||||
case S3C2412_UCON_UCLK:
|
||||
clk->divisor = 1;
|
||||
clk->name = "uclk";
|
||||
break;
|
||||
|
||||
case S3C2412_UCON_PCLK:
|
||||
case S3C2412_UCON_PCLK2:
|
||||
clk->divisor = 1;
|
||||
clk->name = "pclk";
|
||||
break;
|
||||
|
||||
case S3C2412_UCON_USYSCLK:
|
||||
clk->divisor = 1;
|
||||
clk->name = "usysclk";
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int s3c2412_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
dbg("%s: port=%p (%08lx), cfg=%p\n",
|
||||
__func__, port, port->mapbase, cfg);
|
||||
|
||||
/* ensure we don't change the clock settings... */
|
||||
|
||||
ucon &= S3C2412_UCON_CLKMASK;
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon | cfg->ucon);
|
||||
wr_regl(port, S3C2410_ULCON, cfg->ulcon);
|
||||
|
||||
/* reset both fifos */
|
||||
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon | S3C2410_UFCON_RESETBOTH);
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct s3c24xx_uart_info s3c2412_uart_inf = {
|
||||
.name = "Samsung S3C2412 UART",
|
||||
.type = PORT_S3C2412,
|
||||
.fifosize = 64,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S3C2440_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2440_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2440_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2440_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2440_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2440_UFSTAT_TXSHIFT,
|
||||
.get_clksrc = s3c2412_serial_getsource,
|
||||
.set_clksrc = s3c2412_serial_setsource,
|
||||
.reset_port = s3c2412_serial_resetport,
|
||||
};
|
||||
|
||||
/* device management */
|
||||
|
||||
static int s3c2412_serial_probe(struct platform_device *dev)
|
||||
{
|
||||
dbg("s3c2440_serial_probe: dev=%p\n", dev);
|
||||
return s3c24xx_serial_probe(dev, &s3c2412_uart_inf);
|
||||
}
|
||||
|
||||
static struct platform_driver s3c2412_serial_driver = {
|
||||
.probe = s3c2412_serial_probe,
|
||||
.remove = __devexit_p(s3c24xx_serial_remove),
|
||||
.driver = {
|
||||
.name = "s3c2412-uart",
|
||||
.owner = THIS_MODULE,
|
||||
},
|
||||
};
|
||||
|
||||
static inline int s3c2412_serial_init(void)
|
||||
{
|
||||
return s3c24xx_serial_init(&s3c2412_serial_driver, &s3c2412_uart_inf);
|
||||
}
|
||||
|
||||
static inline void s3c2412_serial_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&s3c2412_serial_driver);
|
||||
}
|
||||
|
||||
module_init(s3c2412_serial_init);
|
||||
module_exit(s3c2412_serial_exit);
|
||||
|
||||
MODULE_DESCRIPTION("Samsung S3C2412,S3C2413 SoC Serial port driver");
|
||||
MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>");
|
||||
MODULE_LICENSE("GPL v2");
|
||||
MODULE_ALIAS("platform:s3c2412-uart");
|
|
@ -1,178 +0,0 @@
|
|||
/*
|
||||
* Driver for Samsung S3C2440 and S3C2442 SoC onboard UARTs.
|
||||
*
|
||||
* Ben Dooks, Copyright (c) 2003-2008 Simtec Electronics
|
||||
* http://armlinux.simtec.co.uk/
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#include <linux/module.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/serial_core.h>
|
||||
#include <linux/serial.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
#include <mach/hardware.h>
|
||||
|
||||
#include <plat/regs-serial.h>
|
||||
#include <mach/regs-gpio.h>
|
||||
|
||||
#include "samsung.h"
|
||||
|
||||
|
||||
static int s3c2440_serial_setsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
/* todo - proper fclk<>nonfclk switch. */
|
||||
|
||||
ucon &= ~S3C2440_UCON_CLKMASK;
|
||||
|
||||
if (strcmp(clk->name, "uclk") == 0)
|
||||
ucon |= S3C2440_UCON_UCLK;
|
||||
else if (strcmp(clk->name, "pclk") == 0)
|
||||
ucon |= S3C2440_UCON_PCLK;
|
||||
else if (strcmp(clk->name, "fclk") == 0)
|
||||
ucon |= S3C2440_UCON_FCLK;
|
||||
else {
|
||||
printk(KERN_ERR "unknown clock source %s\n", clk->name);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int s3c2440_serial_getsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
unsigned long ucon0, ucon1, ucon2;
|
||||
|
||||
switch (ucon & S3C2440_UCON_CLKMASK) {
|
||||
case S3C2440_UCON_UCLK:
|
||||
clk->divisor = 1;
|
||||
clk->name = "uclk";
|
||||
break;
|
||||
|
||||
case S3C2440_UCON_PCLK:
|
||||
case S3C2440_UCON_PCLK2:
|
||||
clk->divisor = 1;
|
||||
clk->name = "pclk";
|
||||
break;
|
||||
|
||||
case S3C2440_UCON_FCLK:
|
||||
/* the fun of calculating the uart divisors on
|
||||
* the s3c2440 */
|
||||
|
||||
ucon0 = __raw_readl(S3C24XX_VA_UART0 + S3C2410_UCON);
|
||||
ucon1 = __raw_readl(S3C24XX_VA_UART1 + S3C2410_UCON);
|
||||
ucon2 = __raw_readl(S3C24XX_VA_UART2 + S3C2410_UCON);
|
||||
|
||||
printk("ucons: %08lx, %08lx, %08lx\n", ucon0, ucon1, ucon2);
|
||||
|
||||
ucon0 &= S3C2440_UCON0_DIVMASK;
|
||||
ucon1 &= S3C2440_UCON1_DIVMASK;
|
||||
ucon2 &= S3C2440_UCON2_DIVMASK;
|
||||
|
||||
if (ucon0 != 0) {
|
||||
clk->divisor = ucon0 >> S3C2440_UCON_DIVSHIFT;
|
||||
clk->divisor += 6;
|
||||
} else if (ucon1 != 0) {
|
||||
clk->divisor = ucon1 >> S3C2440_UCON_DIVSHIFT;
|
||||
clk->divisor += 21;
|
||||
} else if (ucon2 != 0) {
|
||||
clk->divisor = ucon2 >> S3C2440_UCON_DIVSHIFT;
|
||||
clk->divisor += 36;
|
||||
} else {
|
||||
/* manual calims 44, seems to be 9 */
|
||||
clk->divisor = 9;
|
||||
}
|
||||
|
||||
clk->name = "fclk";
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int s3c2440_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
dbg("s3c2440_serial_resetport: port=%p (%08lx), cfg=%p\n",
|
||||
port, port->mapbase, cfg);
|
||||
|
||||
/* ensure we don't change the clock settings... */
|
||||
|
||||
ucon &= (S3C2440_UCON0_DIVMASK | (3<<10));
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon | cfg->ucon);
|
||||
wr_regl(port, S3C2410_ULCON, cfg->ulcon);
|
||||
|
||||
/* reset both fifos */
|
||||
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon | S3C2410_UFCON_RESETBOTH);
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct s3c24xx_uart_info s3c2440_uart_inf = {
|
||||
.name = "Samsung S3C2440 UART",
|
||||
.type = PORT_S3C2440,
|
||||
.fifosize = 64,
|
||||
.rx_fifomask = S3C2440_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2440_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2440_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2440_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2440_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2440_UFSTAT_TXSHIFT,
|
||||
.get_clksrc = s3c2440_serial_getsource,
|
||||
.set_clksrc = s3c2440_serial_setsource,
|
||||
.reset_port = s3c2440_serial_resetport,
|
||||
};
|
||||
|
||||
/* device management */
|
||||
|
||||
static int s3c2440_serial_probe(struct platform_device *dev)
|
||||
{
|
||||
dbg("s3c2440_serial_probe: dev=%p\n", dev);
|
||||
return s3c24xx_serial_probe(dev, &s3c2440_uart_inf);
|
||||
}
|
||||
|
||||
static struct platform_driver s3c2440_serial_driver = {
|
||||
.probe = s3c2440_serial_probe,
|
||||
.remove = __devexit_p(s3c24xx_serial_remove),
|
||||
.driver = {
|
||||
.name = "s3c2440-uart",
|
||||
.owner = THIS_MODULE,
|
||||
},
|
||||
};
|
||||
|
||||
static int __init s3c2440_serial_init(void)
|
||||
{
|
||||
return s3c24xx_serial_init(&s3c2440_serial_driver, &s3c2440_uart_inf);
|
||||
}
|
||||
|
||||
static void __exit s3c2440_serial_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&s3c2440_serial_driver);
|
||||
}
|
||||
|
||||
module_init(s3c2440_serial_init);
|
||||
module_exit(s3c2440_serial_exit);
|
||||
|
||||
MODULE_DESCRIPTION("Samsung S3C2440,S3C2442 SoC Serial port driver");
|
||||
MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>");
|
||||
MODULE_LICENSE("GPL v2");
|
||||
MODULE_ALIAS("platform:s3c2440-uart");
|
|
@ -1,149 +0,0 @@
|
|||
/*
|
||||
* Driver for Samsung S3C6400 and S3C6410 SoC onboard UARTs.
|
||||
*
|
||||
* Copyright 2008 Openmoko, Inc.
|
||||
* Copyright 2008 Simtec Electronics
|
||||
* Ben Dooks <ben@simtec.co.uk>
|
||||
* http://armlinux.simtec.co.uk/
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#include <linux/module.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/serial_core.h>
|
||||
#include <linux/serial.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
#include <mach/hardware.h>
|
||||
|
||||
#include <plat/regs-serial.h>
|
||||
|
||||
#include "samsung.h"
|
||||
|
||||
static int s3c6400_serial_setsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
if (strcmp(clk->name, "uclk0") == 0) {
|
||||
ucon &= ~S3C6400_UCON_CLKMASK;
|
||||
ucon |= S3C6400_UCON_UCLK0;
|
||||
} else if (strcmp(clk->name, "uclk1") == 0)
|
||||
ucon |= S3C6400_UCON_UCLK1;
|
||||
else if (strcmp(clk->name, "pclk") == 0) {
|
||||
/* See notes about transitioning from UCLK to PCLK */
|
||||
ucon &= ~S3C6400_UCON_UCLK0;
|
||||
} else {
|
||||
printk(KERN_ERR "unknown clock source %s\n", clk->name);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int s3c6400_serial_getsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
u32 ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
clk->divisor = 1;
|
||||
|
||||
switch (ucon & S3C6400_UCON_CLKMASK) {
|
||||
case S3C6400_UCON_UCLK0:
|
||||
clk->name = "uclk0";
|
||||
break;
|
||||
|
||||
case S3C6400_UCON_UCLK1:
|
||||
clk->name = "uclk1";
|
||||
break;
|
||||
|
||||
case S3C6400_UCON_PCLK:
|
||||
case S3C6400_UCON_PCLK2:
|
||||
clk->name = "pclk";
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int s3c6400_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
dbg("s3c6400_serial_resetport: port=%p (%08lx), cfg=%p\n",
|
||||
port, port->mapbase, cfg);
|
||||
|
||||
/* ensure we don't change the clock settings... */
|
||||
|
||||
ucon &= S3C6400_UCON_CLKMASK;
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon | cfg->ucon);
|
||||
wr_regl(port, S3C2410_ULCON, cfg->ulcon);
|
||||
|
||||
/* reset both fifos */
|
||||
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon | S3C2410_UFCON_RESETBOTH);
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct s3c24xx_uart_info s3c6400_uart_inf = {
|
||||
.name = "Samsung S3C6400 UART",
|
||||
.type = PORT_S3C6400,
|
||||
.fifosize = 64,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S3C2440_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2440_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2440_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2440_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2440_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2440_UFSTAT_TXSHIFT,
|
||||
.get_clksrc = s3c6400_serial_getsource,
|
||||
.set_clksrc = s3c6400_serial_setsource,
|
||||
.reset_port = s3c6400_serial_resetport,
|
||||
};
|
||||
|
||||
/* device management */
|
||||
|
||||
static int s3c6400_serial_probe(struct platform_device *dev)
|
||||
{
|
||||
dbg("s3c6400_serial_probe: dev=%p\n", dev);
|
||||
return s3c24xx_serial_probe(dev, &s3c6400_uart_inf);
|
||||
}
|
||||
|
||||
static struct platform_driver s3c6400_serial_driver = {
|
||||
.probe = s3c6400_serial_probe,
|
||||
.remove = __devexit_p(s3c24xx_serial_remove),
|
||||
.driver = {
|
||||
.name = "s3c6400-uart",
|
||||
.owner = THIS_MODULE,
|
||||
},
|
||||
};
|
||||
|
||||
static int __init s3c6400_serial_init(void)
|
||||
{
|
||||
return s3c24xx_serial_init(&s3c6400_serial_driver, &s3c6400_uart_inf);
|
||||
}
|
||||
|
||||
static void __exit s3c6400_serial_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&s3c6400_serial_driver);
|
||||
}
|
||||
|
||||
module_init(s3c6400_serial_init);
|
||||
module_exit(s3c6400_serial_exit);
|
||||
|
||||
MODULE_DESCRIPTION("Samsung S3C6400,S3C6410 SoC Serial port driver");
|
||||
MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>");
|
||||
MODULE_LICENSE("GPL v2");
|
||||
MODULE_ALIAS("platform:s3c6400-uart");
|
|
@ -1,158 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2010 Samsung Electronics Co., Ltd.
|
||||
* http://www.samsung.com/
|
||||
*
|
||||
* Based on drivers/serial/s3c6400.c
|
||||
*
|
||||
* Driver for Samsung S5PV210 SoC UARTs.
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License version 2 as
|
||||
* published by the Free Software Foundation.
|
||||
*/
|
||||
|
||||
#include <linux/module.h>
|
||||
#include <linux/ioport.h>
|
||||
#include <linux/io.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/init.h>
|
||||
#include <linux/serial_core.h>
|
||||
#include <linux/serial.h>
|
||||
#include <linux/delay.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
#include <mach/hardware.h>
|
||||
#include <plat/regs-serial.h>
|
||||
#include "samsung.h"
|
||||
|
||||
static int s5pv210_serial_setsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
struct s3c2410_uartcfg *cfg = port->dev->platform_data;
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
if (cfg->flags & NO_NEED_CHECK_CLKSRC)
|
||||
return 0;
|
||||
|
||||
if (strcmp(clk->name, "pclk") == 0)
|
||||
ucon &= ~S5PV210_UCON_CLKMASK;
|
||||
else if (strcmp(clk->name, "uclk1") == 0)
|
||||
ucon |= S5PV210_UCON_CLKMASK;
|
||||
else {
|
||||
printk(KERN_ERR "unknown clock source %s\n", clk->name);
|
||||
return -EINVAL;
|
||||
}
|
||||
|
||||
wr_regl(port, S3C2410_UCON, ucon);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
static int s5pv210_serial_getsource(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clk)
|
||||
{
|
||||
struct s3c2410_uartcfg *cfg = port->dev->platform_data;
|
||||
u32 ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
clk->divisor = 1;
|
||||
|
||||
if (cfg->flags & NO_NEED_CHECK_CLKSRC)
|
||||
return 0;
|
||||
|
||||
switch (ucon & S5PV210_UCON_CLKMASK) {
|
||||
case S5PV210_UCON_PCLK:
|
||||
clk->name = "pclk";
|
||||
break;
|
||||
case S5PV210_UCON_UCLK:
|
||||
clk->name = "uclk1";
|
||||
break;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int s5pv210_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
{
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
||||
ucon &= S5PV210_UCON_CLKMASK;
|
||||
wr_regl(port, S3C2410_UCON, ucon | cfg->ucon);
|
||||
wr_regl(port, S3C2410_ULCON, cfg->ulcon);
|
||||
|
||||
/* reset both fifos */
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon | S3C2410_UFCON_RESETBOTH);
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon);
|
||||
|
||||
/* It is need to delay When reset FIFO register */
|
||||
udelay(1);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define S5PV210_UART_DEFAULT_INFO(fifo_size) \
|
||||
.name = "Samsung S5PV210 UART0", \
|
||||
.type = PORT_S3C6400, \
|
||||
.fifosize = fifo_size, \
|
||||
.has_divslot = 1, \
|
||||
.rx_fifomask = S5PV210_UFSTAT_RXMASK, \
|
||||
.rx_fifoshift = S5PV210_UFSTAT_RXSHIFT, \
|
||||
.rx_fifofull = S5PV210_UFSTAT_RXFULL, \
|
||||
.tx_fifofull = S5PV210_UFSTAT_TXFULL, \
|
||||
.tx_fifomask = S5PV210_UFSTAT_TXMASK, \
|
||||
.tx_fifoshift = S5PV210_UFSTAT_TXSHIFT, \
|
||||
.get_clksrc = s5pv210_serial_getsource, \
|
||||
.set_clksrc = s5pv210_serial_setsource, \
|
||||
.reset_port = s5pv210_serial_resetport
|
||||
|
||||
static struct s3c24xx_uart_info s5p_port_fifo256 = {
|
||||
S5PV210_UART_DEFAULT_INFO(256),
|
||||
};
|
||||
|
||||
static struct s3c24xx_uart_info s5p_port_fifo64 = {
|
||||
S5PV210_UART_DEFAULT_INFO(64),
|
||||
};
|
||||
|
||||
static struct s3c24xx_uart_info s5p_port_fifo16 = {
|
||||
S5PV210_UART_DEFAULT_INFO(16),
|
||||
};
|
||||
|
||||
static struct s3c24xx_uart_info *s5p_uart_inf[] = {
|
||||
[0] = &s5p_port_fifo256,
|
||||
[1] = &s5p_port_fifo64,
|
||||
[2] = &s5p_port_fifo16,
|
||||
[3] = &s5p_port_fifo16,
|
||||
};
|
||||
|
||||
/* device management */
|
||||
static int s5p_serial_probe(struct platform_device *pdev)
|
||||
{
|
||||
return s3c24xx_serial_probe(pdev, s5p_uart_inf[pdev->id]);
|
||||
}
|
||||
|
||||
static struct platform_driver s5p_serial_driver = {
|
||||
.probe = s5p_serial_probe,
|
||||
.remove = __devexit_p(s3c24xx_serial_remove),
|
||||
.driver = {
|
||||
.name = "s5pv210-uart",
|
||||
.owner = THIS_MODULE,
|
||||
},
|
||||
};
|
||||
|
||||
static int __init s5p_serial_init(void)
|
||||
{
|
||||
return s3c24xx_serial_init(&s5p_serial_driver, *s5p_uart_inf);
|
||||
}
|
||||
|
||||
static void __exit s5p_serial_exit(void)
|
||||
{
|
||||
platform_driver_unregister(&s5p_serial_driver);
|
||||
}
|
||||
|
||||
module_init(s5p_serial_init);
|
||||
module_exit(s5p_serial_exit);
|
||||
|
||||
MODULE_LICENSE("GPL");
|
||||
MODULE_ALIAS("platform:s5pv210-uart");
|
||||
MODULE_DESCRIPTION("Samsung S5PV210 UART Driver support");
|
||||
MODULE_AUTHOR("Thomas Abraham <thomas.ab@samsung.com>");
|
|
@ -42,6 +42,7 @@
|
|||
#include <linux/delay.h>
|
||||
#include <linux/clk.h>
|
||||
#include <linux/cpufreq.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
#include <asm/irq.h>
|
||||
|
||||
|
@ -49,6 +50,7 @@
|
|||
#include <mach/map.h>
|
||||
|
||||
#include <plat/regs-serial.h>
|
||||
#include <plat/clock.h>
|
||||
|
||||
#include "samsung.h"
|
||||
|
||||
|
@ -190,10 +192,13 @@ static inline struct s3c24xx_uart_info *s3c24xx_port_to_info(struct uart_port *p
|
|||
|
||||
static inline struct s3c2410_uartcfg *s3c24xx_port_to_cfg(struct uart_port *port)
|
||||
{
|
||||
struct s3c24xx_uart_port *ourport;
|
||||
|
||||
if (port->dev == NULL)
|
||||
return NULL;
|
||||
|
||||
return (struct s3c2410_uartcfg *)port->dev->platform_data;
|
||||
ourport = container_of(port, struct s3c24xx_uart_port, port);
|
||||
return ourport->cfg;
|
||||
}
|
||||
|
||||
static int s3c24xx_serial_rx_fifocnt(struct s3c24xx_uart_port *ourport,
|
||||
|
@ -202,7 +207,7 @@ static int s3c24xx_serial_rx_fifocnt(struct s3c24xx_uart_port *ourport,
|
|||
struct s3c24xx_uart_info *info = ourport->info;
|
||||
|
||||
if (ufstat & info->rx_fifofull)
|
||||
return info->fifosize;
|
||||
return ourport->port.fifosize;
|
||||
|
||||
return (ufstat & info->rx_fifomask) >> info->rx_fifoshift;
|
||||
}
|
||||
|
@ -555,154 +560,98 @@ static void s3c24xx_serial_pm(struct uart_port *port, unsigned int level,
|
|||
*
|
||||
*/
|
||||
|
||||
#define MAX_CLK_NAME_LENGTH 15
|
||||
|
||||
#define MAX_CLKS (8)
|
||||
|
||||
static struct s3c24xx_uart_clksrc tmp_clksrc = {
|
||||
.name = "pclk",
|
||||
.min_baud = 0,
|
||||
.max_baud = 0,
|
||||
.divisor = 1,
|
||||
};
|
||||
|
||||
static inline int
|
||||
s3c24xx_serial_getsource(struct uart_port *port, struct s3c24xx_uart_clksrc *c)
|
||||
static inline int s3c24xx_serial_getsource(struct uart_port *port)
|
||||
{
|
||||
struct s3c24xx_uart_info *info = s3c24xx_port_to_info(port);
|
||||
unsigned int ucon;
|
||||
|
||||
return (info->get_clksrc)(port, c);
|
||||
}
|
||||
|
||||
static inline int
|
||||
s3c24xx_serial_setsource(struct uart_port *port, struct s3c24xx_uart_clksrc *c)
|
||||
{
|
||||
struct s3c24xx_uart_info *info = s3c24xx_port_to_info(port);
|
||||
|
||||
return (info->set_clksrc)(port, c);
|
||||
}
|
||||
|
||||
struct baud_calc {
|
||||
struct s3c24xx_uart_clksrc *clksrc;
|
||||
unsigned int calc;
|
||||
unsigned int divslot;
|
||||
unsigned int quot;
|
||||
struct clk *src;
|
||||
};
|
||||
|
||||
static int s3c24xx_serial_calcbaud(struct baud_calc *calc,
|
||||
struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc *clksrc,
|
||||
unsigned int baud)
|
||||
{
|
||||
struct s3c24xx_uart_port *ourport = to_ourport(port);
|
||||
unsigned long rate;
|
||||
|
||||
calc->src = clk_get(port->dev, clksrc->name);
|
||||
if (calc->src == NULL || IS_ERR(calc->src))
|
||||
if (info->num_clks == 1)
|
||||
return 0;
|
||||
|
||||
rate = clk_get_rate(calc->src);
|
||||
rate /= clksrc->divisor;
|
||||
|
||||
calc->clksrc = clksrc;
|
||||
|
||||
if (ourport->info->has_divslot) {
|
||||
unsigned long div = rate / baud;
|
||||
|
||||
/* The UDIVSLOT register on the newer UARTs allows us to
|
||||
* get a divisor adjustment of 1/16th on the baud clock.
|
||||
*
|
||||
* We don't keep the UDIVSLOT value (the 16ths we calculated
|
||||
* by not multiplying the baud by 16) as it is easy enough
|
||||
* to recalculate.
|
||||
*/
|
||||
|
||||
calc->quot = div / 16;
|
||||
calc->calc = rate / div;
|
||||
} else {
|
||||
calc->quot = (rate + (8 * baud)) / (16 * baud);
|
||||
calc->calc = (rate / (calc->quot * 16));
|
||||
}
|
||||
|
||||
calc->quot--;
|
||||
return 1;
|
||||
ucon = rd_regl(port, S3C2410_UCON);
|
||||
ucon &= info->clksel_mask;
|
||||
return ucon >> info->clksel_shift;
|
||||
}
|
||||
|
||||
static unsigned int s3c24xx_serial_getclk(struct uart_port *port,
|
||||
struct s3c24xx_uart_clksrc **clksrc,
|
||||
struct clk **clk,
|
||||
unsigned int baud)
|
||||
static void s3c24xx_serial_setsource(struct uart_port *port,
|
||||
unsigned int clk_sel)
|
||||
{
|
||||
struct s3c2410_uartcfg *cfg = s3c24xx_port_to_cfg(port);
|
||||
struct s3c24xx_uart_clksrc *clkp;
|
||||
struct baud_calc res[MAX_CLKS];
|
||||
struct baud_calc *resptr, *best, *sptr;
|
||||
int i;
|
||||
struct s3c24xx_uart_info *info = s3c24xx_port_to_info(port);
|
||||
unsigned int ucon;
|
||||
|
||||
clkp = cfg->clocks;
|
||||
best = NULL;
|
||||
if (info->num_clks == 1)
|
||||
return;
|
||||
|
||||
if (cfg->clocks_size < 2) {
|
||||
if (cfg->clocks_size == 0)
|
||||
clkp = &tmp_clksrc;
|
||||
ucon = rd_regl(port, S3C2410_UCON);
|
||||
if ((ucon & info->clksel_mask) >> info->clksel_shift == clk_sel)
|
||||
return;
|
||||
|
||||
/* check to see if we're sourcing fclk, and if so we're
|
||||
* going to have to update the clock source
|
||||
*/
|
||||
ucon &= ~info->clksel_mask;
|
||||
ucon |= clk_sel << info->clksel_shift;
|
||||
wr_regl(port, S3C2410_UCON, ucon);
|
||||
}
|
||||
|
||||
if (strcmp(clkp->name, "fclk") == 0) {
|
||||
struct s3c24xx_uart_clksrc src;
|
||||
static unsigned int s3c24xx_serial_getclk(struct s3c24xx_uart_port *ourport,
|
||||
unsigned int req_baud, struct clk **best_clk,
|
||||
unsigned int *clk_num)
|
||||
{
|
||||
struct s3c24xx_uart_info *info = ourport->info;
|
||||
struct clk *clk;
|
||||
unsigned long rate;
|
||||
unsigned int cnt, baud, quot, clk_sel, best_quot = 0;
|
||||
char clkname[MAX_CLK_NAME_LENGTH];
|
||||
int calc_deviation, deviation = (1 << 30) - 1;
|
||||
|
||||
s3c24xx_serial_getsource(port, &src);
|
||||
*best_clk = NULL;
|
||||
clk_sel = (ourport->cfg->clk_sel) ? ourport->cfg->clk_sel :
|
||||
ourport->info->def_clk_sel;
|
||||
for (cnt = 0; cnt < info->num_clks; cnt++) {
|
||||
if (!(clk_sel & (1 << cnt)))
|
||||
continue;
|
||||
|
||||
/* check that the port already using fclk, and if
|
||||
* not, then re-select fclk
|
||||
sprintf(clkname, "clk_uart_baud%d", cnt);
|
||||
clk = clk_get(ourport->port.dev, clkname);
|
||||
if (IS_ERR_OR_NULL(clk))
|
||||
continue;
|
||||
|
||||
rate = clk_get_rate(clk);
|
||||
if (!rate)
|
||||
continue;
|
||||
|
||||
if (ourport->info->has_divslot) {
|
||||
unsigned long div = rate / req_baud;
|
||||
|
||||
/* The UDIVSLOT register on the newer UARTs allows us to
|
||||
* get a divisor adjustment of 1/16th on the baud clock.
|
||||
*
|
||||
* We don't keep the UDIVSLOT value (the 16ths we
|
||||
* calculated by not multiplying the baud by 16) as it
|
||||
* is easy enough to recalculate.
|
||||
*/
|
||||
|
||||
if (strcmp(src.name, clkp->name) == 0) {
|
||||
s3c24xx_serial_setsource(port, clkp);
|
||||
s3c24xx_serial_getsource(port, &src);
|
||||
}
|
||||
|
||||
clkp->divisor = src.divisor;
|
||||
quot = div / 16;
|
||||
baud = rate / div;
|
||||
} else {
|
||||
quot = (rate + (8 * req_baud)) / (16 * req_baud);
|
||||
baud = rate / (quot * 16);
|
||||
}
|
||||
quot--;
|
||||
|
||||
s3c24xx_serial_calcbaud(res, port, clkp, baud);
|
||||
best = res;
|
||||
resptr = best + 1;
|
||||
} else {
|
||||
resptr = res;
|
||||
calc_deviation = req_baud - baud;
|
||||
if (calc_deviation < 0)
|
||||
calc_deviation = -calc_deviation;
|
||||
|
||||
for (i = 0; i < cfg->clocks_size; i++, clkp++) {
|
||||
if (s3c24xx_serial_calcbaud(resptr, port, clkp, baud))
|
||||
resptr++;
|
||||
if (calc_deviation < deviation) {
|
||||
*best_clk = clk;
|
||||
best_quot = quot;
|
||||
*clk_num = cnt;
|
||||
deviation = calc_deviation;
|
||||
}
|
||||
}
|
||||
|
||||
/* ok, we now need to select the best clock we found */
|
||||
|
||||
if (!best) {
|
||||
unsigned int deviation = (1<<30)|((1<<30)-1);
|
||||
int calc_deviation;
|
||||
|
||||
for (sptr = res; sptr < resptr; sptr++) {
|
||||
calc_deviation = baud - sptr->calc;
|
||||
if (calc_deviation < 0)
|
||||
calc_deviation = -calc_deviation;
|
||||
|
||||
if (calc_deviation < deviation) {
|
||||
best = sptr;
|
||||
deviation = calc_deviation;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* store results to pass back */
|
||||
|
||||
*clksrc = best->clksrc;
|
||||
*clk = best->src;
|
||||
|
||||
return best->quot;
|
||||
return best_quot;
|
||||
}
|
||||
|
||||
/* udivslot_table[]
|
||||
|
@ -735,10 +684,9 @@ static void s3c24xx_serial_set_termios(struct uart_port *port,
|
|||
{
|
||||
struct s3c2410_uartcfg *cfg = s3c24xx_port_to_cfg(port);
|
||||
struct s3c24xx_uart_port *ourport = to_ourport(port);
|
||||
struct s3c24xx_uart_clksrc *clksrc = NULL;
|
||||
struct clk *clk = NULL;
|
||||
unsigned long flags;
|
||||
unsigned int baud, quot;
|
||||
unsigned int baud, quot, clk_sel = 0;
|
||||
unsigned int ulcon;
|
||||
unsigned int umcon;
|
||||
unsigned int udivslot = 0;
|
||||
|
@ -754,17 +702,16 @@ static void s3c24xx_serial_set_termios(struct uart_port *port,
|
|||
*/
|
||||
|
||||
baud = uart_get_baud_rate(port, termios, old, 0, 115200*8);
|
||||
|
||||
quot = s3c24xx_serial_getclk(ourport, baud, &clk, &clk_sel);
|
||||
if (baud == 38400 && (port->flags & UPF_SPD_MASK) == UPF_SPD_CUST)
|
||||
quot = port->custom_divisor;
|
||||
else
|
||||
quot = s3c24xx_serial_getclk(port, &clksrc, &clk, baud);
|
||||
if (!clk)
|
||||
return;
|
||||
|
||||
/* check to see if we need to change clock source */
|
||||
|
||||
if (ourport->clksrc != clksrc || ourport->baudclk != clk) {
|
||||
dbg("selecting clock %p\n", clk);
|
||||
s3c24xx_serial_setsource(port, clksrc);
|
||||
if (ourport->baudclk != clk) {
|
||||
s3c24xx_serial_setsource(port, clk_sel);
|
||||
|
||||
if (ourport->baudclk != NULL && !IS_ERR(ourport->baudclk)) {
|
||||
clk_disable(ourport->baudclk);
|
||||
|
@ -773,7 +720,6 @@ static void s3c24xx_serial_set_termios(struct uart_port *port,
|
|||
|
||||
clk_enable(clk);
|
||||
|
||||
ourport->clksrc = clksrc;
|
||||
ourport->baudclk = clk;
|
||||
ourport->baudclk_rate = clk ? clk_get_rate(clk) : 0;
|
||||
}
|
||||
|
@ -1020,16 +966,29 @@ static struct s3c24xx_uart_port s3c24xx_serial_ports[CONFIG_SERIAL_SAMSUNG_UARTS
|
|||
|
||||
/* s3c24xx_serial_resetport
|
||||
*
|
||||
* wrapper to call the specific reset for this port (reset the fifos
|
||||
* and the settings)
|
||||
* reset the fifos and other the settings.
|
||||
*/
|
||||
|
||||
static inline int s3c24xx_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
static void s3c24xx_serial_resetport(struct uart_port *port,
|
||||
struct s3c2410_uartcfg *cfg)
|
||||
{
|
||||
struct s3c24xx_uart_info *info = s3c24xx_port_to_info(port);
|
||||
unsigned long ucon = rd_regl(port, S3C2410_UCON);
|
||||
unsigned int ucon_mask;
|
||||
|
||||
return (info->reset_port)(port, cfg);
|
||||
ucon_mask = info->clksel_mask;
|
||||
if (info->type == PORT_S3C2440)
|
||||
ucon_mask |= S3C2440_UCON0_DIVMASK;
|
||||
|
||||
ucon &= ucon_mask;
|
||||
wr_regl(port, S3C2410_UCON, ucon | cfg->ucon);
|
||||
|
||||
/* reset both fifos */
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon | S3C2410_UFCON_RESETBOTH);
|
||||
wr_regl(port, S3C2410_UFCON, cfg->ufcon);
|
||||
|
||||
/* some delay is required after fifo reset */
|
||||
udelay(1);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1121,11 +1080,10 @@ static inline void s3c24xx_serial_cpufreq_deregister(struct s3c24xx_uart_port *p
|
|||
*/
|
||||
|
||||
static int s3c24xx_serial_init_port(struct s3c24xx_uart_port *ourport,
|
||||
struct s3c24xx_uart_info *info,
|
||||
struct platform_device *platdev)
|
||||
{
|
||||
struct uart_port *port = &ourport->port;
|
||||
struct s3c2410_uartcfg *cfg;
|
||||
struct s3c2410_uartcfg *cfg = ourport->cfg;
|
||||
struct resource *res;
|
||||
int ret;
|
||||
|
||||
|
@ -1134,30 +1092,16 @@ static int s3c24xx_serial_init_port(struct s3c24xx_uart_port *ourport,
|
|||
if (platdev == NULL)
|
||||
return -ENODEV;
|
||||
|
||||
cfg = s3c24xx_dev_to_cfg(&platdev->dev);
|
||||
|
||||
if (port->mapbase != 0)
|
||||
return 0;
|
||||
|
||||
if (cfg->hwport > CONFIG_SERIAL_SAMSUNG_UARTS) {
|
||||
printk(KERN_ERR "%s: port %d bigger than %d\n", __func__,
|
||||
cfg->hwport, CONFIG_SERIAL_SAMSUNG_UARTS);
|
||||
return -ERANGE;
|
||||
}
|
||||
|
||||
/* setup info for port */
|
||||
port->dev = &platdev->dev;
|
||||
ourport->info = info;
|
||||
|
||||
/* Startup sequence is different for s3c64xx and higher SoC's */
|
||||
if (s3c24xx_serial_has_interrupt_mask(port))
|
||||
s3c24xx_serial_ops.startup = s3c64xx_serial_startup;
|
||||
|
||||
/* copy the info in from provided structure */
|
||||
ourport->port.fifosize = info->fifosize;
|
||||
|
||||
dbg("s3c24xx_serial_init_port: %p (hw %d)...\n", port, cfg->hwport);
|
||||
|
||||
port->uartclk = 1;
|
||||
|
||||
if (cfg->uart_flags & UPF_CONS_FLOW) {
|
||||
|
@ -1215,43 +1159,74 @@ static ssize_t s3c24xx_serial_show_clksrc(struct device *dev,
|
|||
struct uart_port *port = s3c24xx_dev_to_port(dev);
|
||||
struct s3c24xx_uart_port *ourport = to_ourport(port);
|
||||
|
||||
return snprintf(buf, PAGE_SIZE, "* %s\n", ourport->clksrc->name);
|
||||
return snprintf(buf, PAGE_SIZE, "* %s\n", ourport->baudclk->name);
|
||||
}
|
||||
|
||||
static DEVICE_ATTR(clock_source, S_IRUGO, s3c24xx_serial_show_clksrc, NULL);
|
||||
|
||||
|
||||
/* Device driver serial port probe */
|
||||
|
||||
static const struct of_device_id s3c24xx_uart_dt_match[];
|
||||
static int probe_index;
|
||||
|
||||
int s3c24xx_serial_probe(struct platform_device *dev,
|
||||
struct s3c24xx_uart_info *info)
|
||||
static inline struct s3c24xx_serial_drv_data *s3c24xx_get_driver_data(
|
||||
struct platform_device *pdev)
|
||||
{
|
||||
#ifdef CONFIG_OF
|
||||
if (pdev->dev.of_node) {
|
||||
const struct of_device_id *match;
|
||||
match = of_match_node(s3c24xx_uart_dt_match, pdev->dev.of_node);
|
||||
return (struct s3c24xx_serial_drv_data *)match->data;
|
||||
}
|
||||
#endif
|
||||
return (struct s3c24xx_serial_drv_data *)
|
||||
platform_get_device_id(pdev)->driver_data;
|
||||
}
|
||||
|
||||
static int s3c24xx_serial_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct s3c24xx_uart_port *ourport;
|
||||
int ret;
|
||||
|
||||
dbg("s3c24xx_serial_probe(%p, %p) %d\n", dev, info, probe_index);
|
||||
dbg("s3c24xx_serial_probe(%p) %d\n", pdev, probe_index);
|
||||
|
||||
ourport = &s3c24xx_serial_ports[probe_index];
|
||||
|
||||
ourport->drv_data = s3c24xx_get_driver_data(pdev);
|
||||
if (!ourport->drv_data) {
|
||||
dev_err(&pdev->dev, "could not find driver data\n");
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
ourport->info = ourport->drv_data->info;
|
||||
ourport->cfg = (pdev->dev.platform_data) ?
|
||||
(struct s3c2410_uartcfg *)pdev->dev.platform_data :
|
||||
ourport->drv_data->def_cfg;
|
||||
|
||||
ourport->port.fifosize = (ourport->info->fifosize) ?
|
||||
ourport->info->fifosize :
|
||||
ourport->drv_data->fifosize[probe_index];
|
||||
|
||||
probe_index++;
|
||||
|
||||
dbg("%s: initialising port %p...\n", __func__, ourport);
|
||||
|
||||
ret = s3c24xx_serial_init_port(ourport, info, dev);
|
||||
ret = s3c24xx_serial_init_port(ourport, pdev);
|
||||
if (ret < 0)
|
||||
goto probe_err;
|
||||
|
||||
dbg("%s: adding port\n", __func__);
|
||||
uart_add_one_port(&s3c24xx_uart_drv, &ourport->port);
|
||||
platform_set_drvdata(dev, &ourport->port);
|
||||
platform_set_drvdata(pdev, &ourport->port);
|
||||
|
||||
ret = device_create_file(&dev->dev, &dev_attr_clock_source);
|
||||
ret = device_create_file(&pdev->dev, &dev_attr_clock_source);
|
||||
if (ret < 0)
|
||||
printk(KERN_ERR "%s: failed to add clksrc attr.\n", __func__);
|
||||
dev_err(&pdev->dev, "failed to add clock source attr.\n");
|
||||
|
||||
ret = s3c24xx_serial_cpufreq_register(ourport);
|
||||
if (ret < 0)
|
||||
dev_err(&dev->dev, "failed to add cpufreq notifier\n");
|
||||
dev_err(&pdev->dev, "failed to add cpufreq notifier\n");
|
||||
|
||||
return 0;
|
||||
|
||||
|
@ -1259,9 +1234,7 @@ int s3c24xx_serial_probe(struct platform_device *dev,
|
|||
return ret;
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(s3c24xx_serial_probe);
|
||||
|
||||
int __devexit s3c24xx_serial_remove(struct platform_device *dev)
|
||||
static int __devexit s3c24xx_serial_remove(struct platform_device *dev)
|
||||
{
|
||||
struct uart_port *port = s3c24xx_dev_to_port(&dev->dev);
|
||||
|
||||
|
@ -1274,8 +1247,6 @@ int __devexit s3c24xx_serial_remove(struct platform_device *dev)
|
|||
return 0;
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(s3c24xx_serial_remove);
|
||||
|
||||
/* UART power management code */
|
||||
#ifdef CONFIG_PM_SLEEP
|
||||
static int s3c24xx_serial_suspend(struct device *dev)
|
||||
|
@ -1315,41 +1286,6 @@ static const struct dev_pm_ops s3c24xx_serial_pm_ops = {
|
|||
#define SERIAL_SAMSUNG_PM_OPS NULL
|
||||
#endif /* CONFIG_PM_SLEEP */
|
||||
|
||||
int s3c24xx_serial_init(struct platform_driver *drv,
|
||||
struct s3c24xx_uart_info *info)
|
||||
{
|
||||
dbg("s3c24xx_serial_init(%p,%p)\n", drv, info);
|
||||
|
||||
drv->driver.pm = SERIAL_SAMSUNG_PM_OPS;
|
||||
|
||||
return platform_driver_register(drv);
|
||||
}
|
||||
|
||||
EXPORT_SYMBOL_GPL(s3c24xx_serial_init);
|
||||
|
||||
/* module initialisation code */
|
||||
|
||||
static int __init s3c24xx_serial_modinit(void)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = uart_register_driver(&s3c24xx_uart_drv);
|
||||
if (ret < 0) {
|
||||
printk(KERN_ERR "failed to register UART driver\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static void __exit s3c24xx_serial_modexit(void)
|
||||
{
|
||||
uart_unregister_driver(&s3c24xx_uart_drv);
|
||||
}
|
||||
|
||||
module_init(s3c24xx_serial_modinit);
|
||||
module_exit(s3c24xx_serial_modexit);
|
||||
|
||||
/* Console code */
|
||||
|
||||
#ifdef CONFIG_SERIAL_SAMSUNG_CONSOLE
|
||||
|
@ -1395,12 +1331,13 @@ static void __init
|
|||
s3c24xx_serial_get_options(struct uart_port *port, int *baud,
|
||||
int *parity, int *bits)
|
||||
{
|
||||
struct s3c24xx_uart_clksrc clksrc;
|
||||
struct clk *clk;
|
||||
unsigned int ulcon;
|
||||
unsigned int ucon;
|
||||
unsigned int ubrdiv;
|
||||
unsigned long rate;
|
||||
unsigned int clk_sel;
|
||||
char clk_name[MAX_CLK_NAME_LENGTH];
|
||||
|
||||
ulcon = rd_regl(port, S3C2410_ULCON);
|
||||
ucon = rd_regl(port, S3C2410_UCON);
|
||||
|
@ -1445,44 +1382,21 @@ s3c24xx_serial_get_options(struct uart_port *port, int *baud,
|
|||
|
||||
/* now calculate the baud rate */
|
||||
|
||||
s3c24xx_serial_getsource(port, &clksrc);
|
||||
clk_sel = s3c24xx_serial_getsource(port);
|
||||
sprintf(clk_name, "clk_uart_baud%d", clk_sel);
|
||||
|
||||
clk = clk_get(port->dev, clksrc.name);
|
||||
clk = clk_get(port->dev, clk_name);
|
||||
if (!IS_ERR(clk) && clk != NULL)
|
||||
rate = clk_get_rate(clk) / clksrc.divisor;
|
||||
rate = clk_get_rate(clk);
|
||||
else
|
||||
rate = 1;
|
||||
|
||||
|
||||
*baud = rate / (16 * (ubrdiv + 1));
|
||||
dbg("calculated baud %d\n", *baud);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/* s3c24xx_serial_init_ports
|
||||
*
|
||||
* initialise the serial ports from the machine provided initialisation
|
||||
* data.
|
||||
*/
|
||||
|
||||
static int s3c24xx_serial_init_ports(struct s3c24xx_uart_info **info)
|
||||
{
|
||||
struct s3c24xx_uart_port *ptr = s3c24xx_serial_ports;
|
||||
struct platform_device **platdev_ptr;
|
||||
int i;
|
||||
|
||||
dbg("s3c24xx_serial_init_ports: initialising ports...\n");
|
||||
|
||||
platdev_ptr = s3c24xx_uart_devs;
|
||||
|
||||
for (i = 0; i < CONFIG_SERIAL_SAMSUNG_UARTS; i++, ptr++, platdev_ptr++) {
|
||||
s3c24xx_serial_init_port(ptr, info[i], *platdev_ptr);
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int __init
|
||||
s3c24xx_serial_console_setup(struct console *co, char *options)
|
||||
{
|
||||
|
@ -1526,11 +1440,6 @@ s3c24xx_serial_console_setup(struct console *co, char *options)
|
|||
return uart_set_options(port, co, baud, parity, bits, flow);
|
||||
}
|
||||
|
||||
/* s3c24xx_serial_initconsole
|
||||
*
|
||||
* initialise the console from one of the uart drivers
|
||||
*/
|
||||
|
||||
static struct console s3c24xx_serial_console = {
|
||||
.name = S3C24XX_SERIAL_NAME,
|
||||
.device = uart_console_device,
|
||||
|
@ -1540,34 +1449,250 @@ static struct console s3c24xx_serial_console = {
|
|||
.setup = s3c24xx_serial_console_setup,
|
||||
.data = &s3c24xx_uart_drv,
|
||||
};
|
||||
|
||||
int s3c24xx_serial_initconsole(struct platform_driver *drv,
|
||||
struct s3c24xx_uart_info **info)
|
||||
|
||||
{
|
||||
struct platform_device *dev = s3c24xx_uart_devs[0];
|
||||
|
||||
dbg("s3c24xx_serial_initconsole\n");
|
||||
|
||||
/* select driver based on the cpu */
|
||||
|
||||
if (dev == NULL) {
|
||||
printk(KERN_ERR "s3c24xx: no devices for console init\n");
|
||||
return 0;
|
||||
}
|
||||
|
||||
if (strcmp(dev->name, drv->driver.name) != 0)
|
||||
return 0;
|
||||
|
||||
s3c24xx_serial_console.data = &s3c24xx_uart_drv;
|
||||
s3c24xx_serial_init_ports(info);
|
||||
|
||||
register_console(&s3c24xx_serial_console);
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif /* CONFIG_SERIAL_SAMSUNG_CONSOLE */
|
||||
|
||||
#ifdef CONFIG_CPU_S3C2410
|
||||
static struct s3c24xx_serial_drv_data s3c2410_serial_drv_data = {
|
||||
.info = &(struct s3c24xx_uart_info) {
|
||||
.name = "Samsung S3C2410 UART",
|
||||
.type = PORT_S3C2410,
|
||||
.fifosize = 16,
|
||||
.rx_fifomask = S3C2410_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2410_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2410_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2410_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2410_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2410_UFSTAT_TXSHIFT,
|
||||
.def_clk_sel = S3C2410_UCON_CLKSEL0,
|
||||
.num_clks = 2,
|
||||
.clksel_mask = S3C2410_UCON_CLKMASK,
|
||||
.clksel_shift = S3C2410_UCON_CLKSHIFT,
|
||||
},
|
||||
.def_cfg = &(struct s3c2410_uartcfg) {
|
||||
.ucon = S3C2410_UCON_DEFAULT,
|
||||
.ufcon = S3C2410_UFCON_DEFAULT,
|
||||
},
|
||||
};
|
||||
#define S3C2410_SERIAL_DRV_DATA ((kernel_ulong_t)&s3c2410_serial_drv_data)
|
||||
#else
|
||||
#define S3C2410_SERIAL_DRV_DATA (kernel_ulong_t)NULL
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_CPU_S3C2412
|
||||
static struct s3c24xx_serial_drv_data s3c2412_serial_drv_data = {
|
||||
.info = &(struct s3c24xx_uart_info) {
|
||||
.name = "Samsung S3C2412 UART",
|
||||
.type = PORT_S3C2412,
|
||||
.fifosize = 64,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S3C2440_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2440_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2440_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2440_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2440_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2440_UFSTAT_TXSHIFT,
|
||||
.def_clk_sel = S3C2410_UCON_CLKSEL2,
|
||||
.num_clks = 4,
|
||||
.clksel_mask = S3C2412_UCON_CLKMASK,
|
||||
.clksel_shift = S3C2412_UCON_CLKSHIFT,
|
||||
},
|
||||
.def_cfg = &(struct s3c2410_uartcfg) {
|
||||
.ucon = S3C2410_UCON_DEFAULT,
|
||||
.ufcon = S3C2410_UFCON_DEFAULT,
|
||||
},
|
||||
};
|
||||
#define S3C2412_SERIAL_DRV_DATA ((kernel_ulong_t)&s3c2412_serial_drv_data)
|
||||
#else
|
||||
#define S3C2412_SERIAL_DRV_DATA (kernel_ulong_t)NULL
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_CPU_S3C2440) || defined(CONFIG_CPU_S3C2416) || \
|
||||
defined(CONFIG_CPU_S3C2443)
|
||||
static struct s3c24xx_serial_drv_data s3c2440_serial_drv_data = {
|
||||
.info = &(struct s3c24xx_uart_info) {
|
||||
.name = "Samsung S3C2440 UART",
|
||||
.type = PORT_S3C2440,
|
||||
.fifosize = 64,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S3C2440_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2440_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2440_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2440_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2440_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2440_UFSTAT_TXSHIFT,
|
||||
.def_clk_sel = S3C2410_UCON_CLKSEL2,
|
||||
.num_clks = 4,
|
||||
.clksel_mask = S3C2412_UCON_CLKMASK,
|
||||
.clksel_shift = S3C2412_UCON_CLKSHIFT,
|
||||
},
|
||||
.def_cfg = &(struct s3c2410_uartcfg) {
|
||||
.ucon = S3C2410_UCON_DEFAULT,
|
||||
.ufcon = S3C2410_UFCON_DEFAULT,
|
||||
},
|
||||
};
|
||||
#define S3C2440_SERIAL_DRV_DATA ((kernel_ulong_t)&s3c2440_serial_drv_data)
|
||||
#else
|
||||
#define S3C2440_SERIAL_DRV_DATA (kernel_ulong_t)NULL
|
||||
#endif
|
||||
|
||||
#if defined(CONFIG_CPU_S3C6400) || defined(CONFIG_CPU_S3C6410) || \
|
||||
defined(CONFIG_CPU_S5P6440) || defined(CONFIG_CPU_S5P6450) || \
|
||||
defined(CONFIG_CPU_S5PC100)
|
||||
static struct s3c24xx_serial_drv_data s3c6400_serial_drv_data = {
|
||||
.info = &(struct s3c24xx_uart_info) {
|
||||
.name = "Samsung S3C6400 UART",
|
||||
.type = PORT_S3C6400,
|
||||
.fifosize = 64,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S3C2440_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S3C2440_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S3C2440_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S3C2440_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S3C2440_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S3C2440_UFSTAT_TXSHIFT,
|
||||
.def_clk_sel = S3C2410_UCON_CLKSEL2,
|
||||
.num_clks = 4,
|
||||
.clksel_mask = S3C6400_UCON_CLKMASK,
|
||||
.clksel_shift = S3C6400_UCON_CLKSHIFT,
|
||||
},
|
||||
.def_cfg = &(struct s3c2410_uartcfg) {
|
||||
.ucon = S3C2410_UCON_DEFAULT,
|
||||
.ufcon = S3C2410_UFCON_DEFAULT,
|
||||
},
|
||||
};
|
||||
#define S3C6400_SERIAL_DRV_DATA ((kernel_ulong_t)&s3c6400_serial_drv_data)
|
||||
#else
|
||||
#define S3C6400_SERIAL_DRV_DATA (kernel_ulong_t)NULL
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_CPU_S5PV210
|
||||
static struct s3c24xx_serial_drv_data s5pv210_serial_drv_data = {
|
||||
.info = &(struct s3c24xx_uart_info) {
|
||||
.name = "Samsung S5PV210 UART",
|
||||
.type = PORT_S3C6400,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S5PV210_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S5PV210_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S5PV210_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S5PV210_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S5PV210_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S5PV210_UFSTAT_TXSHIFT,
|
||||
.def_clk_sel = S3C2410_UCON_CLKSEL0,
|
||||
.num_clks = 2,
|
||||
.clksel_mask = S5PV210_UCON_CLKMASK,
|
||||
.clksel_shift = S5PV210_UCON_CLKSHIFT,
|
||||
},
|
||||
.def_cfg = &(struct s3c2410_uartcfg) {
|
||||
.ucon = S5PV210_UCON_DEFAULT,
|
||||
.ufcon = S5PV210_UFCON_DEFAULT,
|
||||
},
|
||||
.fifosize = { 256, 64, 16, 16 },
|
||||
};
|
||||
#define S5PV210_SERIAL_DRV_DATA ((kernel_ulong_t)&s5pv210_serial_drv_data)
|
||||
#else
|
||||
#define S5PV210_SERIAL_DRV_DATA (kernel_ulong_t)NULL
|
||||
#endif
|
||||
|
||||
#ifdef CONFIG_CPU_EXYNOS4210
|
||||
static struct s3c24xx_serial_drv_data exynos4210_serial_drv_data = {
|
||||
.info = &(struct s3c24xx_uart_info) {
|
||||
.name = "Samsung Exynos4 UART",
|
||||
.type = PORT_S3C6400,
|
||||
.has_divslot = 1,
|
||||
.rx_fifomask = S5PV210_UFSTAT_RXMASK,
|
||||
.rx_fifoshift = S5PV210_UFSTAT_RXSHIFT,
|
||||
.rx_fifofull = S5PV210_UFSTAT_RXFULL,
|
||||
.tx_fifofull = S5PV210_UFSTAT_TXFULL,
|
||||
.tx_fifomask = S5PV210_UFSTAT_TXMASK,
|
||||
.tx_fifoshift = S5PV210_UFSTAT_TXSHIFT,
|
||||
.def_clk_sel = S3C2410_UCON_CLKSEL0,
|
||||
.num_clks = 1,
|
||||
.clksel_mask = 0,
|
||||
.clksel_shift = 0,
|
||||
},
|
||||
.def_cfg = &(struct s3c2410_uartcfg) {
|
||||
.ucon = S5PV210_UCON_DEFAULT,
|
||||
.ufcon = S5PV210_UFCON_DEFAULT,
|
||||
.has_fracval = 1,
|
||||
},
|
||||
.fifosize = { 256, 64, 16, 16 },
|
||||
};
|
||||
#define EXYNOS4210_SERIAL_DRV_DATA ((kernel_ulong_t)&exynos4210_serial_drv_data)
|
||||
#else
|
||||
#define EXYNOS4210_SERIAL_DRV_DATA (kernel_ulong_t)NULL
|
||||
#endif
|
||||
|
||||
static struct platform_device_id s3c24xx_serial_driver_ids[] = {
|
||||
{
|
||||
.name = "s3c2410-uart",
|
||||
.driver_data = S3C2410_SERIAL_DRV_DATA,
|
||||
}, {
|
||||
.name = "s3c2412-uart",
|
||||
.driver_data = S3C2412_SERIAL_DRV_DATA,
|
||||
}, {
|
||||
.name = "s3c2440-uart",
|
||||
.driver_data = S3C2440_SERIAL_DRV_DATA,
|
||||
}, {
|
||||
.name = "s3c6400-uart",
|
||||
.driver_data = S3C6400_SERIAL_DRV_DATA,
|
||||
}, {
|
||||
.name = "s5pv210-uart",
|
||||
.driver_data = S5PV210_SERIAL_DRV_DATA,
|
||||
}, {
|
||||
.name = "exynos4210-uart",
|
||||
.driver_data = EXYNOS4210_SERIAL_DRV_DATA,
|
||||
},
|
||||
{ },
|
||||
};
|
||||
MODULE_DEVICE_TABLE(platform, s3c24xx_serial_driver_ids);
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static const struct of_device_id s3c24xx_uart_dt_match[] = {
|
||||
{ .compatible = "samsung,exynos4210-uart",
|
||||
.data = (void *)EXYNOS4210_SERIAL_DRV_DATA },
|
||||
{},
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, s3c24xx_uart_dt_match);
|
||||
#else
|
||||
#define s3c24xx_uart_dt_match NULL
|
||||
#endif
|
||||
|
||||
static struct platform_driver samsung_serial_driver = {
|
||||
.probe = s3c24xx_serial_probe,
|
||||
.remove = __devexit_p(s3c24xx_serial_remove),
|
||||
.id_table = s3c24xx_serial_driver_ids,
|
||||
.driver = {
|
||||
.name = "samsung-uart",
|
||||
.owner = THIS_MODULE,
|
||||
.pm = SERIAL_SAMSUNG_PM_OPS,
|
||||
.of_match_table = s3c24xx_uart_dt_match,
|
||||
},
|
||||
};
|
||||
|
||||
/* module initialisation code */
|
||||
|
||||
static int __init s3c24xx_serial_modinit(void)
|
||||
{
|
||||
int ret;
|
||||
|
||||
ret = uart_register_driver(&s3c24xx_uart_drv);
|
||||
if (ret < 0) {
|
||||
printk(KERN_ERR "failed to register UART driver\n");
|
||||
return -1;
|
||||
}
|
||||
|
||||
return platform_driver_register(&samsung_serial_driver);
|
||||
}
|
||||
|
||||
static void __exit s3c24xx_serial_modexit(void)
|
||||
{
|
||||
uart_unregister_driver(&s3c24xx_uart_drv);
|
||||
}
|
||||
|
||||
module_init(s3c24xx_serial_modinit);
|
||||
module_exit(s3c24xx_serial_modexit);
|
||||
|
||||
MODULE_ALIAS("platform:samsung-uart");
|
||||
MODULE_DESCRIPTION("Samsung SoC Serial port driver");
|
||||
MODULE_AUTHOR("Ben Dooks <ben@simtec.co.uk>");
|
||||
MODULE_LICENSE("GPL v2");
|
||||
|
|
|
@ -19,20 +19,25 @@ struct s3c24xx_uart_info {
|
|||
unsigned long tx_fifomask;
|
||||
unsigned long tx_fifoshift;
|
||||
unsigned long tx_fifofull;
|
||||
unsigned int def_clk_sel;
|
||||
unsigned long num_clks;
|
||||
unsigned long clksel_mask;
|
||||
unsigned long clksel_shift;
|
||||
|
||||
/* uart port features */
|
||||
|
||||
unsigned int has_divslot:1;
|
||||
|
||||
/* clock source control */
|
||||
|
||||
int (*get_clksrc)(struct uart_port *, struct s3c24xx_uart_clksrc *clk);
|
||||
int (*set_clksrc)(struct uart_port *, struct s3c24xx_uart_clksrc *clk);
|
||||
|
||||
/* uart controls */
|
||||
int (*reset_port)(struct uart_port *, struct s3c2410_uartcfg *);
|
||||
};
|
||||
|
||||
struct s3c24xx_serial_drv_data {
|
||||
struct s3c24xx_uart_info *info;
|
||||
struct s3c2410_uartcfg *def_cfg;
|
||||
unsigned int fifosize[CONFIG_SERIAL_SAMSUNG_UARTS];
|
||||
};
|
||||
|
||||
struct s3c24xx_uart_port {
|
||||
unsigned char rx_claimed;
|
||||
unsigned char tx_claimed;
|
||||
|
@ -43,10 +48,13 @@ struct s3c24xx_uart_port {
|
|||
unsigned int tx_irq;
|
||||
|
||||
struct s3c24xx_uart_info *info;
|
||||
struct s3c24xx_uart_clksrc *clksrc;
|
||||
struct clk *clk;
|
||||
struct clk *baudclk;
|
||||
struct uart_port port;
|
||||
struct s3c24xx_serial_drv_data *drv_data;
|
||||
|
||||
/* reference to platform data */
|
||||
struct s3c2410_uartcfg *cfg;
|
||||
|
||||
#ifdef CONFIG_CPU_FREQ
|
||||
struct notifier_block freq_transition;
|
||||
|
@ -56,7 +64,6 @@ struct s3c24xx_uart_port {
|
|||
/* conversion functions */
|
||||
|
||||
#define s3c24xx_dev_to_port(__dev) (struct uart_port *)dev_get_drvdata(__dev)
|
||||
#define s3c24xx_dev_to_cfg(__dev) (struct s3c2410_uartcfg *)((__dev)->platform_data)
|
||||
|
||||
/* register access controls */
|
||||
|
||||
|
@ -69,17 +76,6 @@ struct s3c24xx_uart_port {
|
|||
#define wr_regb(port, reg, val) __raw_writeb(val, portaddr(port, reg))
|
||||
#define wr_regl(port, reg, val) __raw_writel(val, portaddr(port, reg))
|
||||
|
||||
extern int s3c24xx_serial_probe(struct platform_device *dev,
|
||||
struct s3c24xx_uart_info *uart);
|
||||
|
||||
extern int __devexit s3c24xx_serial_remove(struct platform_device *dev);
|
||||
|
||||
extern int s3c24xx_serial_initconsole(struct platform_driver *drv,
|
||||
struct s3c24xx_uart_info **uart);
|
||||
|
||||
extern int s3c24xx_serial_init(struct platform_driver *drv,
|
||||
struct s3c24xx_uart_info *info);
|
||||
|
||||
#ifdef CONFIG_SERIAL_SAMSUNG_DEBUG
|
||||
|
||||
extern void printascii(const char *);
|
||||
|
|
|
@ -12,17 +12,9 @@
|
|||
#ifndef __AMBA_PL330_H_
|
||||
#define __AMBA_PL330_H_
|
||||
|
||||
#include <linux/dmaengine.h>
|
||||
#include <asm/hardware/pl330.h>
|
||||
|
||||
struct dma_pl330_peri {
|
||||
/*
|
||||
* Peri_Req i/f of the DMAC that is
|
||||
* peripheral could be reached from.
|
||||
*/
|
||||
u8 peri_id; /* specific dma id */
|
||||
enum pl330_reqtype rqtype;
|
||||
};
|
||||
|
||||
struct dma_pl330_platdata {
|
||||
/*
|
||||
* Number of valid peripherals connected to DMAC.
|
||||
|
@ -33,9 +25,12 @@ struct dma_pl330_platdata {
|
|||
*/
|
||||
u8 nr_valid_peri;
|
||||
/* Array of valid peripherals */
|
||||
struct dma_pl330_peri *peri;
|
||||
u8 *peri_id;
|
||||
/* Operational capabilities */
|
||||
dma_cap_mask_t cap_mask;
|
||||
/* Bytes to allocate for MC buffer */
|
||||
unsigned mcbuf_sz;
|
||||
};
|
||||
|
||||
extern bool pl330_filter(struct dma_chan *chan, void *param);
|
||||
#endif /* __AMBA_PL330_H_ */
|
||||
|
|
Загрузка…
Ссылка в новой задаче