Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
fca63efe
Commit
fca63efe
authored
Jun 01, 2017
by
Michael Turquette
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'clk-ap806' into clk-next
parents
658a7568
b90da675
Changes
2
Show whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
86 additions
and
45 deletions
+86
-45
Documentation/devicetree/bindings/arm/marvell/ap806-system-controller.txt
...vicetree/bindings/arm/marvell/ap806-system-controller.txt
+15
-9
drivers/clk/mvebu/ap806-system-controller.c
drivers/clk/mvebu/ap806-system-controller.c
+71
-36
No files found.
Documentation/devicetree/bindings/arm/marvell/ap806-system-controller.txt
View file @
fca63efe
...
@@ -7,6 +7,14 @@ registers giving access to numerous features: clocks, pin-muxing and
...
@@ -7,6 +7,14 @@ registers giving access to numerous features: clocks, pin-muxing and
many other SoC configuration items. This DT binding allows to describe
many other SoC configuration items. This DT binding allows to describe
this system controller.
this system controller.
For the top level node:
- compatible: must be: "syscon", "simple-mfd";
- reg: register area of the AP806 system controller
Clocks:
-------
The Device Tree node representing the AP806 system controller provides
The Device Tree node representing the AP806 system controller provides
a number of clocks:
a number of clocks:
...
@@ -17,19 +25,17 @@ a number of clocks:
...
@@ -17,19 +25,17 @@ a number of clocks:
Required properties:
Required properties:
- compatible: must be:
- compatible: must be: "marvell,ap806-clock"
"marvell,ap806-system-controller", "syscon"
- reg: register area of the AP806 system controller
- #clock-cells: must be set to 1
- #clock-cells: must be set to 1
- clock-output-names: must be defined to:
"ap-cpu-cluster-0", "ap-cpu-cluster-1", "ap-fixed", "ap-mss"
Example:
Example:
syscon: system-controller@6f4000 {
syscon: system-controller@6f4000 {
compatible = "marvell,ap806-system-controller", "syscon";
compatible = "syscon", "simple-mfd";
#clock-cells = <1>;
clock-output-names = "ap-cpu-cluster-0", "ap-cpu-cluster-1",
"ap-fixed", "ap-mss";
reg = <0x6f4000 0x1000>;
reg = <0x6f4000 0x1000>;
ap_clk: clock {
compatible = "marvell,ap806-clock";
#clock-cells = <1>;
};
};
};
drivers/clk/mvebu/ap806-system-controller.c
View file @
fca63efe
...
@@ -32,24 +32,38 @@ static struct clk_onecell_data ap806_clk_data = {
...
@@ -32,24 +32,38 @@ static struct clk_onecell_data ap806_clk_data = {
.
clk_num
=
AP806_CLK_NUM
,
.
clk_num
=
AP806_CLK_NUM
,
};
};
static
int
ap806_syscon_clk_probe
(
struct
platform_device
*
pdev
)
static
char
*
ap806_unique_name
(
struct
device
*
dev
,
struct
device_node
*
np
,
char
*
name
)
{
const
__be32
*
reg
;
u64
addr
;
reg
=
of_get_property
(
np
,
"reg"
,
NULL
);
addr
=
of_translate_address
(
np
,
reg
);
return
devm_kasprintf
(
dev
,
GFP_KERNEL
,
"%llx-%s"
,
(
unsigned
long
long
)
addr
,
name
);
}
static
int
ap806_syscon_common_probe
(
struct
platform_device
*
pdev
,
struct
device_node
*
syscon_node
)
{
{
unsigned
int
freq_mode
,
cpuclk_freq
;
unsigned
int
freq_mode
,
cpuclk_freq
;
const
char
*
name
,
*
fixedclk_name
;
const
char
*
name
,
*
fixedclk_name
;
struct
device_node
*
np
=
pdev
->
dev
.
of_node
;
struct
device
*
dev
=
&
pdev
->
dev
;
struct
device_node
*
np
=
dev
->
of_node
;
struct
regmap
*
regmap
;
struct
regmap
*
regmap
;
u32
reg
;
u32
reg
;
int
ret
;
int
ret
;
regmap
=
syscon_node_to_regmap
(
np
);
regmap
=
syscon_node_to_regmap
(
syscon_node
);
if
(
IS_ERR
(
regmap
))
{
if
(
IS_ERR
(
regmap
))
{
dev_err
(
&
pdev
->
dev
,
"cannot get regmap
\n
"
);
dev_err
(
dev
,
"cannot get regmap
\n
"
);
return
PTR_ERR
(
regmap
);
return
PTR_ERR
(
regmap
);
}
}
ret
=
regmap_read
(
regmap
,
AP806_SAR_REG
,
&
reg
);
ret
=
regmap_read
(
regmap
,
AP806_SAR_REG
,
&
reg
);
if
(
ret
)
{
if
(
ret
)
{
dev_err
(
&
pdev
->
dev
,
"cannot read from regmap
\n
"
);
dev_err
(
dev
,
"cannot read from regmap
\n
"
);
return
ret
;
return
ret
;
}
}
...
@@ -89,7 +103,7 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -89,7 +103,7 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
cpuclk_freq
=
600
;
cpuclk_freq
=
600
;
break
;
break
;
default:
default:
dev_err
(
&
pdev
->
dev
,
"invalid SAR value
\n
"
);
dev_err
(
dev
,
"invalid SAR value
\n
"
);
return
-
EINVAL
;
return
-
EINVAL
;
}
}
...
@@ -97,18 +111,16 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -97,18 +111,16 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
cpuclk_freq
*=
1000
*
1000
;
cpuclk_freq
*=
1000
*
1000
;
/* CPU clocks depend on the Sample At Reset configuration */
/* CPU clocks depend on the Sample At Reset configuration */
of_property_read_string_index
(
np
,
"clock-output-names"
,
name
=
ap806_unique_name
(
dev
,
syscon_node
,
"cpu-cluster-0"
);
0
,
&
name
);
ap806_clks
[
0
]
=
clk_register_fixed_rate
(
dev
,
name
,
NULL
,
ap806_clks
[
0
]
=
clk_register_fixed_rate
(
&
pdev
->
dev
,
name
,
NULL
,
0
,
cpuclk_freq
);
0
,
cpuclk_freq
);
if
(
IS_ERR
(
ap806_clks
[
0
]))
{
if
(
IS_ERR
(
ap806_clks
[
0
]))
{
ret
=
PTR_ERR
(
ap806_clks
[
0
]);
ret
=
PTR_ERR
(
ap806_clks
[
0
]);
goto
fail0
;
goto
fail0
;
}
}
of_property_read_string_index
(
np
,
"clock-output-names"
,
name
=
ap806_unique_name
(
dev
,
syscon_node
,
"cpu-cluster-1"
);
1
,
&
name
);
ap806_clks
[
1
]
=
clk_register_fixed_rate
(
dev
,
name
,
NULL
,
0
,
ap806_clks
[
1
]
=
clk_register_fixed_rate
(
&
pdev
->
dev
,
name
,
NULL
,
0
,
cpuclk_freq
);
cpuclk_freq
);
if
(
IS_ERR
(
ap806_clks
[
1
]))
{
if
(
IS_ERR
(
ap806_clks
[
1
]))
{
ret
=
PTR_ERR
(
ap806_clks
[
1
]);
ret
=
PTR_ERR
(
ap806_clks
[
1
]);
...
@@ -116,9 +128,8 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -116,9 +128,8 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
}
}
/* Fixed clock is always 1200 Mhz */
/* Fixed clock is always 1200 Mhz */
of_property_read_string_index
(
np
,
"clock-output-names"
,
fixedclk_name
=
ap806_unique_name
(
dev
,
syscon_node
,
"fixed"
);
2
,
&
fixedclk_name
);
ap806_clks
[
2
]
=
clk_register_fixed_rate
(
dev
,
fixedclk_name
,
NULL
,
ap806_clks
[
2
]
=
clk_register_fixed_rate
(
&
pdev
->
dev
,
fixedclk_name
,
NULL
,
0
,
1200
*
1000
*
1000
);
0
,
1200
*
1000
*
1000
);
if
(
IS_ERR
(
ap806_clks
[
2
]))
{
if
(
IS_ERR
(
ap806_clks
[
2
]))
{
ret
=
PTR_ERR
(
ap806_clks
[
2
]);
ret
=
PTR_ERR
(
ap806_clks
[
2
]);
...
@@ -126,8 +137,7 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -126,8 +137,7 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
}
}
/* MSS Clock is fixed clock divided by 6 */
/* MSS Clock is fixed clock divided by 6 */
of_property_read_string_index
(
np
,
"clock-output-names"
,
name
=
ap806_unique_name
(
dev
,
syscon_node
,
"mss"
);
3
,
&
name
);
ap806_clks
[
3
]
=
clk_register_fixed_factor
(
NULL
,
name
,
fixedclk_name
,
ap806_clks
[
3
]
=
clk_register_fixed_factor
(
NULL
,
name
,
fixedclk_name
,
0
,
1
,
6
);
0
,
1
,
6
);
if
(
IS_ERR
(
ap806_clks
[
3
]))
{
if
(
IS_ERR
(
ap806_clks
[
3
]))
{
...
@@ -135,13 +145,8 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -135,13 +145,8 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
goto
fail3
;
goto
fail3
;
}
}
/* eMMC Clock is fixed clock divided by 3 */
/* SDIO(/eMMC) Clock is fixed clock divided by 3 */
if
(
of_property_read_string_index
(
np
,
"clock-output-names"
,
name
=
ap806_unique_name
(
dev
,
syscon_node
,
"sdio"
);
4
,
&
name
))
{
ap806_clk_data
.
clk_num
--
;
dev_warn
(
&
pdev
->
dev
,
"eMMC clock missing: update the device tree!
\n
"
);
}
else
{
ap806_clks
[
4
]
=
clk_register_fixed_factor
(
NULL
,
name
,
ap806_clks
[
4
]
=
clk_register_fixed_factor
(
NULL
,
name
,
fixedclk_name
,
fixedclk_name
,
0
,
1
,
3
);
0
,
1
,
3
);
...
@@ -149,7 +154,6 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -149,7 +154,6 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
ret
=
PTR_ERR
(
ap806_clks
[
4
]);
ret
=
PTR_ERR
(
ap806_clks
[
4
]);
goto
fail4
;
goto
fail4
;
}
}
}
of_clk_add_provider
(
np
,
of_clk_src_onecell_get
,
&
ap806_clk_data
);
of_clk_add_provider
(
np
,
of_clk_src_onecell_get
,
&
ap806_clk_data
);
ret
=
of_clk_add_provider
(
np
,
of_clk_src_onecell_get
,
&
ap806_clk_data
);
ret
=
of_clk_add_provider
(
np
,
of_clk_src_onecell_get
,
&
ap806_clk_data
);
...
@@ -172,17 +176,48 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
...
@@ -172,17 +176,48 @@ static int ap806_syscon_clk_probe(struct platform_device *pdev)
return
ret
;
return
ret
;
}
}
static
const
struct
of_device_id
ap806_syscon_of_match
[]
=
{
static
int
ap806_syscon_legacy_probe
(
struct
platform_device
*
pdev
)
{
dev_warn
(
&
pdev
->
dev
,
FW_WARN
"Using legacy device tree binding
\n
"
);
dev_warn
(
&
pdev
->
dev
,
FW_WARN
"Update your device tree:
\n
"
);
dev_warn
(
&
pdev
->
dev
,
FW_WARN
"This binding won't be supported in future kernel
\n
"
);
return
ap806_syscon_common_probe
(
pdev
,
pdev
->
dev
.
of_node
);
}
static
int
ap806_clock_probe
(
struct
platform_device
*
pdev
)
{
return
ap806_syscon_common_probe
(
pdev
,
pdev
->
dev
.
of_node
->
parent
);
}
static
const
struct
of_device_id
ap806_syscon_legacy_of_match
[]
=
{
{
.
compatible
=
"marvell,ap806-system-controller"
,
},
{
.
compatible
=
"marvell,ap806-system-controller"
,
},
{
}
{
}
};
};
static
struct
platform_driver
ap806_syscon_driver
=
{
static
struct
platform_driver
ap806_syscon_
legacy_
driver
=
{
.
probe
=
ap806_syscon_
clk
_probe
,
.
probe
=
ap806_syscon_
legacy
_probe
,
.
driver
=
{
.
driver
=
{
.
name
=
"marvell-ap806-system-controller"
,
.
name
=
"marvell-ap806-system-controller"
,
.
of_match_table
=
ap806_syscon_of_match
,
.
of_match_table
=
ap806_syscon_legacy_of_match
,
.
suppress_bind_attrs
=
true
,
},
};
builtin_platform_driver
(
ap806_syscon_legacy_driver
);
static
const
struct
of_device_id
ap806_clock_of_match
[]
=
{
{
.
compatible
=
"marvell,ap806-clock"
,
},
{
}
};
static
struct
platform_driver
ap806_clock_driver
=
{
.
probe
=
ap806_clock_probe
,
.
driver
=
{
.
name
=
"marvell-ap806-clock"
,
.
of_match_table
=
ap806_clock_of_match
,
.
suppress_bind_attrs
=
true
,
.
suppress_bind_attrs
=
true
,
},
},
};
};
builtin_platform_driver
(
ap806_
syscon
_driver
);
builtin_platform_driver
(
ap806_
clock
_driver
);
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment