Skip to content
GitLab
Menu
Projects
Groups
Snippets
Loading...
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
Menu
Open sidebar
adam.huang
Arm Trusted Firmware
Commits
0412c66a
Commit
0412c66a
authored
Feb 25, 2015
by
danh-arm
Browse files
Merge pull request #259 from soby-mathew/sm/plat_max_afflvl
Export maximum affinity using PLATFORM_MAX_AFFLVL macro
parents
f578d5e1
8c32bc26
Changes
11
Hide whitespace changes
Inline
Side-by-side
docs/porting-guide.md
View file @
0412c66a
...
@@ -181,6 +181,17 @@ file is found in [plat/fvp/include/platform_def.h].
...
@@ -181,6 +181,17 @@ file is found in [plat/fvp/include/platform_def.h].
Defines the total number of nodes in the affinity heirarchy at all affinity
Defines the total number of nodes in the affinity heirarchy at all affinity
levels used by the platform.
levels used by the platform.
*
**#define : PLATFORM_MAX_AFFLVL**
Defines the maximum affinity level that the power management operations
should apply to. ARMv8-A has support for 4 affinity levels. It is likely
that hardware will implement fewer affinity levels. This macro allows the
PSCI implementation to consider only those affinity levels in the system
that the platform implements. For example, the Base AEM FVP implements two
clusters with a configurable number of CPUs. It reports the maximum
affinity level as 1, resulting in PSCI power control up to the cluster
level.
*
**#define : BL1_RO_BASE**
*
**#define : BL1_RO_BASE**
Defines the base address in secure ROM where BL1 originally lives. Must be
Defines the base address in secure ROM where BL1 originally lives. Must be
...
@@ -1131,25 +1142,6 @@ is missing but needs to be accounted for to reach this single CPU in the
...
@@ -1131,25 +1142,6 @@ is missing but needs to be accounted for to reach this single CPU in the
topology tree. Hence it is marked as
`PSCI_AFF_ABSENT`
.
topology tree. Hence it is marked as
`PSCI_AFF_ABSENT`
.
### Function : plat_get_max_afflvl() [mandatory]
Argument : void
Return : int
This function may execute with the MMU and data caches enabled if the platform
port does the necessary initializations in
`bl31_plat_arch_setup()`
. It is only
called by the primary CPU.
This function is called by the PSCI implementation both during cold and warm
boot, to determine the maximum affinity level that the power management
operations should apply to. ARMv8-A has support for 4 affinity levels. It is
likely that hardware will implement fewer affinity levels. This function allows
the PSCI implementation to consider only those affinity levels in the system
that the platform implements. For example, the Base AEM FVP implements two
clusters with a configurable number of CPUs. It reports the maximum affinity
level as 1, resulting in PSCI power control up to the cluster level.
### Function : platform_setup_pm() [mandatory]
### Function : platform_setup_pm() [mandatory]
Argument : const plat_pm_ops **
Argument : const plat_pm_ops **
...
...
include/plat/common/platform.h
View file @
0412c66a
...
@@ -177,7 +177,6 @@ struct entry_point_info *bl31_plat_get_next_image_ep_info(uint32_t type);
...
@@ -177,7 +177,6 @@ struct entry_point_info *bl31_plat_get_next_image_ep_info(uint32_t type);
* Mandatory PSCI functions (BL3-1)
* Mandatory PSCI functions (BL3-1)
******************************************************************************/
******************************************************************************/
int
platform_setup_pm
(
const
struct
plat_pm_ops
**
);
int
platform_setup_pm
(
const
struct
plat_pm_ops
**
);
int
plat_get_max_afflvl
(
void
);
unsigned
int
plat_get_aff_count
(
unsigned
int
,
unsigned
long
);
unsigned
int
plat_get_aff_count
(
unsigned
int
,
unsigned
long
);
unsigned
int
plat_get_aff_state
(
unsigned
int
,
unsigned
long
);
unsigned
int
plat_get_aff_state
(
unsigned
int
,
unsigned
long
);
...
...
plat/fvp/fvp_topology.c
View file @
0412c66a
...
@@ -176,15 +176,6 @@ unsigned int plat_get_aff_state(unsigned int aff_lvl,
...
@@ -176,15 +176,6 @@ unsigned int plat_get_aff_state(unsigned int aff_lvl,
return
aff_state
;
return
aff_state
;
}
}
/*******************************************************************************
* Handy optimization to prevent the psci implementation from traversing through
* affinity levels which are not present while detecting the platform topology.
******************************************************************************/
int
plat_get_max_afflvl
(
void
)
{
return
MPIDR_AFFLVL1
;
}
/*******************************************************************************
/*******************************************************************************
* This function populates the FVP specific topology information depending upon
* This function populates the FVP specific topology information depending upon
* the FVP flavour its running on. We construct all the mpidrs we can handle
* the FVP flavour its running on. We construct all the mpidrs we can handle
...
...
plat/fvp/include/platform_def.h
View file @
0412c66a
...
@@ -105,6 +105,7 @@
...
@@ -105,6 +105,7 @@
#define PLATFORM_MAX_CPUS_PER_CLUSTER 4
#define PLATFORM_MAX_CPUS_PER_CLUSTER 4
#define PLATFORM_NUM_AFFS (PLATFORM_CLUSTER_COUNT + \
#define PLATFORM_NUM_AFFS (PLATFORM_CLUSTER_COUNT + \
PLATFORM_CORE_COUNT)
PLATFORM_CORE_COUNT)
#define PLATFORM_MAX_AFFLVL MPIDR_AFFLVL1
#define MAX_IO_DEVICES 3
#define MAX_IO_DEVICES 3
#define MAX_IO_HANDLES 4
#define MAX_IO_HANDLES 4
...
...
plat/juno/include/platform_def.h
View file @
0412c66a
...
@@ -92,6 +92,7 @@
...
@@ -92,6 +92,7 @@
#define PLATFORM_CORE_COUNT 6
#define PLATFORM_CORE_COUNT 6
#define PLATFORM_NUM_AFFS (PLATFORM_CLUSTER_COUNT + \
#define PLATFORM_NUM_AFFS (PLATFORM_CLUSTER_COUNT + \
PLATFORM_CORE_COUNT)
PLATFORM_CORE_COUNT)
#define PLATFORM_MAX_AFFLVL MPIDR_AFFLVL1
#define MAX_IO_DEVICES 3
#define MAX_IO_DEVICES 3
#define MAX_IO_HANDLES 4
#define MAX_IO_HANDLES 4
...
...
plat/juno/juno_private.h
View file @
0412c66a
...
@@ -157,7 +157,6 @@ void plat_gic_init(void);
...
@@ -157,7 +157,6 @@ void plat_gic_init(void);
/* Declarations for plat_topology.c */
/* Declarations for plat_topology.c */
int
plat_setup_topology
(
void
);
int
plat_setup_topology
(
void
);
int
plat_get_max_afflvl
(
void
);
unsigned
int
plat_get_aff_count
(
unsigned
int
aff_lvl
,
unsigned
long
mpidr
);
unsigned
int
plat_get_aff_count
(
unsigned
int
aff_lvl
,
unsigned
long
mpidr
);
unsigned
int
plat_get_aff_state
(
unsigned
int
aff_lvl
,
unsigned
long
mpidr
);
unsigned
int
plat_get_aff_state
(
unsigned
int
aff_lvl
,
unsigned
long
mpidr
);
...
...
plat/juno/plat_topology.c
View file @
0412c66a
...
@@ -48,11 +48,6 @@ unsigned int plat_get_aff_state(unsigned int aff_lvl, unsigned long mpidr)
...
@@ -48,11 +48,6 @@ unsigned int plat_get_aff_state(unsigned int aff_lvl, unsigned long mpidr)
return
aff_lvl
<=
MPIDR_AFFLVL1
?
PSCI_AFF_PRESENT
:
PSCI_AFF_ABSENT
;
return
aff_lvl
<=
MPIDR_AFFLVL1
?
PSCI_AFF_PRESENT
:
PSCI_AFF_ABSENT
;
}
}
int
plat_get_max_afflvl
()
{
return
MPIDR_AFFLVL1
;
}
int
plat_setup_topology
()
int
plat_setup_topology
()
{
{
/* Juno todo: Make topology configurable via SCC */
/* Juno todo: Make topology configurable via SCC */
...
...
services/std_svc/psci/psci_common.c
View file @
0412c66a
...
@@ -61,6 +61,13 @@ __attribute__ ((section("tzfw_coherent_mem")))
...
@@ -61,6 +61,13 @@ __attribute__ ((section("tzfw_coherent_mem")))
******************************************************************************/
******************************************************************************/
const
plat_pm_ops_t
*
psci_plat_pm_ops
;
const
plat_pm_ops_t
*
psci_plat_pm_ops
;
/*******************************************************************************
* Check that the maximum affinity level supported by the platform makes sense
* ****************************************************************************/
CASSERT
(
PLATFORM_MAX_AFFLVL
<=
MPIDR_MAX_AFFLVL
&&
\
PLATFORM_MAX_AFFLVL
>=
MPIDR_AFFLVL0
,
\
assert_platform_max_afflvl_check
);
/*******************************************************************************
/*******************************************************************************
* This function is passed an array of pointers to affinity level nodes in the
* This function is passed an array of pointers to affinity level nodes in the
* topology tree for an mpidr. It iterates through the nodes to find the highest
* topology tree for an mpidr. It iterates through the nodes to find the highest
...
@@ -150,29 +157,15 @@ int get_power_on_target_afflvl()
...
@@ -150,29 +157,15 @@ int get_power_on_target_afflvl()
/*
/*
* Assume that this cpu was suspended and retrieve its target affinity
* Assume that this cpu was suspended and retrieve its target affinity
* level. If it is invalid then it could only have been turned off
* level. If it is invalid then it could only have been turned off
* earlier.
get_max_afflvl() will return
the highest affinity level a
* earlier.
PLATFORM_MAX_AFFLVL will be
the highest affinity level a
* cpu can be turned off to.
* cpu can be turned off to.
*/
*/
afflvl
=
psci_get_suspend_afflvl
();
afflvl
=
psci_get_suspend_afflvl
();
if
(
afflvl
==
PSCI_INVALID_DATA
)
if
(
afflvl
==
PSCI_INVALID_DATA
)
afflvl
=
get_max_afflvl
()
;
afflvl
=
PLATFORM_MAX_AFFLVL
;
return
afflvl
;
return
afflvl
;
}
}
/*******************************************************************************
* Simple routine to retrieve the maximum affinity level supported by the
* platform and check that it makes sense.
******************************************************************************/
int
get_max_afflvl
(
void
)
{
int
aff_lvl
;
aff_lvl
=
plat_get_max_afflvl
();
assert
(
aff_lvl
<=
MPIDR_MAX_AFFLVL
&&
aff_lvl
>=
MPIDR_AFFLVL0
);
return
aff_lvl
;
}
/*******************************************************************************
/*******************************************************************************
* Simple routine to set the id of an affinity instance at a given level in the
* Simple routine to set the id of an affinity instance at a given level in the
* mpidr.
* mpidr.
...
@@ -204,7 +197,7 @@ unsigned long mpidr_set_aff_inst(unsigned long mpidr,
...
@@ -204,7 +197,7 @@ unsigned long mpidr_set_aff_inst(unsigned long mpidr,
int
psci_check_afflvl_range
(
int
start_afflvl
,
int
end_afflvl
)
int
psci_check_afflvl_range
(
int
start_afflvl
,
int
end_afflvl
)
{
{
/* Sanity check the parameters passed */
/* Sanity check the parameters passed */
if
(
end_afflvl
>
get_max_afflvl
()
)
if
(
end_afflvl
>
PLATFORM_MAX_AFFLVL
)
return
PSCI_E_INVALID_PARAMS
;
return
PSCI_E_INVALID_PARAMS
;
if
(
start_afflvl
<
MPIDR_AFFLVL0
)
if
(
start_afflvl
<
MPIDR_AFFLVL0
)
...
...
services/std_svc/psci/psci_main.c
View file @
0412c66a
...
@@ -78,7 +78,7 @@ int psci_cpu_on(unsigned long target_cpu,
...
@@ -78,7 +78,7 @@ int psci_cpu_on(unsigned long target_cpu,
* levels need to be turned on
* levels need to be turned on
*/
*/
start_afflvl
=
MPIDR_AFFLVL0
;
start_afflvl
=
MPIDR_AFFLVL0
;
end_afflvl
=
get_max_afflvl
()
;
end_afflvl
=
PLATFORM_MAX_AFFLVL
;
rc
=
psci_afflvl_on
(
target_cpu
,
rc
=
psci_afflvl_on
(
target_cpu
,
&
ep
,
&
ep
,
start_afflvl
,
start_afflvl
,
...
@@ -106,7 +106,7 @@ int psci_cpu_suspend(unsigned int power_state,
...
@@ -106,7 +106,7 @@ int psci_cpu_suspend(unsigned int power_state,
/* Sanity check the requested state */
/* Sanity check the requested state */
target_afflvl
=
psci_get_pstate_afflvl
(
power_state
);
target_afflvl
=
psci_get_pstate_afflvl
(
power_state
);
if
(
target_afflvl
>
get_max_afflvl
()
)
if
(
target_afflvl
>
PLATFORM_MAX_AFFLVL
)
return
PSCI_E_INVALID_PARAMS
;
return
PSCI_E_INVALID_PARAMS
;
/* Validate the power_state using platform pm_ops */
/* Validate the power_state using platform pm_ops */
...
@@ -170,7 +170,7 @@ int psci_cpu_suspend(unsigned int power_state,
...
@@ -170,7 +170,7 @@ int psci_cpu_suspend(unsigned int power_state,
int
psci_cpu_off
(
void
)
int
psci_cpu_off
(
void
)
{
{
int
rc
;
int
rc
;
int
target_afflvl
=
get_max_afflvl
()
;
int
target_afflvl
=
PLATFORM_MAX_AFFLVL
;
/*
/*
* Traverse from the highest to the lowest affinity level. When the
* Traverse from the highest to the lowest affinity level. When the
...
@@ -196,7 +196,7 @@ int psci_affinity_info(unsigned long target_affinity,
...
@@ -196,7 +196,7 @@ int psci_affinity_info(unsigned long target_affinity,
unsigned
int
aff_state
;
unsigned
int
aff_state
;
aff_map_node_t
*
node
;
aff_map_node_t
*
node
;
if
(
lowest_affinity_level
>
get_max_afflvl
()
)
if
(
lowest_affinity_level
>
PLATFORM_MAX_AFFLVL
)
return
rc
;
return
rc
;
node
=
psci_get_aff_map_node
(
target_affinity
,
lowest_affinity_level
);
node
=
psci_get_aff_map_node
(
target_affinity
,
lowest_affinity_level
);
...
...
services/std_svc/psci/psci_private.h
View file @
0412c66a
...
@@ -113,7 +113,6 @@ extern const spd_pm_ops_t *psci_spd_pm;
...
@@ -113,7 +113,6 @@ extern const spd_pm_ops_t *psci_spd_pm;
* Function prototypes
* Function prototypes
******************************************************************************/
******************************************************************************/
/* Private exported functions from psci_common.c */
/* Private exported functions from psci_common.c */
int
get_max_afflvl
(
void
);
unsigned
short
psci_get_state
(
aff_map_node_t
*
node
);
unsigned
short
psci_get_state
(
aff_map_node_t
*
node
);
unsigned
short
psci_get_phys_state
(
aff_map_node_t
*
node
);
unsigned
short
psci_get_phys_state
(
aff_map_node_t
*
node
);
void
psci_set_state
(
aff_map_node_t
*
node
,
unsigned
short
state
);
void
psci_set_state
(
aff_map_node_t
*
node
,
unsigned
short
state
);
...
...
services/std_svc/psci/psci_setup.c
View file @
0412c66a
...
@@ -107,7 +107,7 @@ aff_map_node_t *psci_get_aff_map_node(unsigned long mpidr, int aff_lvl)
...
@@ -107,7 +107,7 @@ aff_map_node_t *psci_get_aff_map_node(unsigned long mpidr, int aff_lvl)
{
{
int
rc
;
int
rc
;
if
(
aff_lvl
>
get_max_afflvl
()
)
if
(
aff_lvl
>
PLATFORM_MAX_AFFLVL
)
return
NULL
;
return
NULL
;
/* Right shift the mpidr to the required affinity level */
/* Right shift the mpidr to the required affinity level */
...
@@ -320,7 +320,7 @@ int32_t psci_setup(void)
...
@@ -320,7 +320,7 @@ int32_t psci_setup(void)
psci_plat_pm_ops
=
NULL
;
psci_plat_pm_ops
=
NULL
;
/* Find out the maximum affinity level that the platform implements */
/* Find out the maximum affinity level that the platform implements */
max_afflvl
=
get_max_afflvl
()
;
max_afflvl
=
PLATFORM_MAX_AFFLVL
;
assert
(
max_afflvl
<=
MPIDR_MAX_AFFLVL
);
assert
(
max_afflvl
<=
MPIDR_MAX_AFFLVL
);
/*
/*
...
...
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