From e598dab7f300aad26b3b9590c4865e4f3af9800e Mon Sep 17 00:00:00 2001 From: Santosh Puranik Date: Mon, 20 Jun 2016 04:36:35 -0500 Subject: PPE Multicast implementation Change-Id: I01ac5566e80ba5a0a539f58cddc3f22fd763e63b Reviewed-on: http://ralgit01.raleigh.ibm.com/gerrit1/26114 Tested-by: Jenkins Server Reviewed-by: Sachin Gupta Reviewed-by: Gregory S. Still Reviewed-by: Santosh S. Puranik --- hwpf/include/plat/target.H | 280 ++++++++------------------------------------- 1 file changed, 47 insertions(+), 233 deletions(-) (limited to 'hwpf/include/plat/target.H') diff --git a/hwpf/include/plat/target.H b/hwpf/include/plat/target.H index f61e40dd..9ed8de29 100644 --- a/hwpf/include/plat/target.H +++ b/hwpf/include/plat/target.H @@ -33,6 +33,7 @@ #include #include #include +#include #include #include #include @@ -43,12 +44,6 @@ extern "C" extern std::vector G_vec_targets; } -static const uint8_t CORES_PER_QUAD = 4; -static const uint8_t EX_PER_QUAD = 2; -static const uint8_t CORES_PER_EX = 2; -static const uint8_t N3_CHIPLET = 5; -static const uint8_t MCS_PER_MCBIST = 2; - struct ScomAddr { ScomAddr(uint32_t i_addr) : iv_addr(i_addr) @@ -130,78 +125,6 @@ namespace fapi2 return PPE_TARGET_TYPE_PERV; } - /// @brief Create a Target, with a value - /// @param[in] Value the value (i.e., specific element this - /// target represents, or pointer) - /// @note Platforms can mangle the value and K to get a - /// single uint64_t in value which represents all the information - /// they might need. value( K | V ), for example - /// - template - Target::Target(V Value) - { - uint32_t l_plat_argument = Value.value; - // Already formed target handle? - if(Value.fields.valid == 1) - { - this->iv_handle = Value; - return; - } - - this->iv_handle.value = 0; - if(K & TARGET_TYPE_PROC_CHIP) - { - this->iv_handle.fields.chiplet_num = 0; - this->iv_handle.fields.type = PPE_TARGET_TYPE_PROC_CHIP; - this->iv_handle.fields.type_target_num = 0; - } - else if(K & TARGET_TYPE_PERV) - { - this->iv_handle.fields.chiplet_num = l_plat_argument + NEST_GROUP1_CHIPLET_OFFSET; - this->iv_handle.fields.type = PPE_TARGET_TYPE_PERV; - this->iv_handle.fields.type_target_num = l_plat_argument; - } - else if(K & TARGET_TYPE_CORE) - { - this->iv_handle.fields.chiplet_num = l_plat_argument + CORE_CHIPLET_OFFSET; - this->iv_handle.fields.type = PPE_TARGET_TYPE_CORE | PPE_TARGET_TYPE_PERV; - this->iv_handle.fields.type_target_num = l_plat_argument; - } - else if(K & TARGET_TYPE_EQ) - { - this->iv_handle.fields.chiplet_num = l_plat_argument + EQ_CHIPLET_OFFSET; - this->iv_handle.fields.type = PPE_TARGET_TYPE_EQ | PPE_TARGET_TYPE_PERV; - this->iv_handle.fields.type_target_num = l_plat_argument; - } - else if(K & TARGET_TYPE_EX) - { - this->iv_handle.fields.chiplet_num = (l_plat_argument / 2) + EX_CHIPLET_OFFSET; - this->iv_handle.fields.type = PPE_TARGET_TYPE_EX; - this->iv_handle.fields.type_target_num = l_plat_argument; - } - else if(K & TARGET_TYPE_MCBIST) - { - - this->iv_handle.fields.chiplet_num = l_plat_argument + MCBIST_CHIPLET_OFFSET; - this->iv_handle.fields.type = PPE_TARGET_TYPE_MCBIST | PPE_TARGET_TYPE_PERV; - this->iv_handle.fields.type_target_num = l_plat_argument; - } - else if(K & TARGET_TYPE_MCS) - { - this->iv_handle.fields.chiplet_num = N3_CHIPLET - (MCS_PER_MCBIST * (l_plat_argument / MCS_PER_MCBIST)); - this->iv_handle.fields.type = PPE_TARGET_TYPE_MCS; - this->iv_handle.fields.type_target_num = l_plat_argument; - } - else if(K == TARGET_TYPE_ALL) - { - this->iv_handle.fields.chiplet_num = l_plat_argument; - this->iv_handle.fields.type = PPE_TARGET_TYPE_ALL; - } - - this->iv_handle.fields.valid = 1; - - } - /// /// @brief Assignment Operator. /// @param[in] i_right Reference to Target to assign from. @@ -248,17 +171,20 @@ namespace fapi2 /// /// @brief Get this target's immediate parent /// @tparam T The type of the parent - /// @return Target a target representing the parent + /// @return Target a target representing the parent /// template template - inline Target Target::getParent(void) const + inline Target Target::getParent(void) const { static_assert(((K == TARGET_TYPE_EQ) || (K == TARGET_TYPE_CORE) || (K == TARGET_TYPE_MCBIST) || (K == TARGET_TYPE_PERV) || - (K == TARGET_TYPE_EX)) && + (K == TARGET_TYPE_EX) || + (K == TARGET_TYPE_PROC_CHIP) || + (K == (TARGET_TYPE_PROC_CHIP | TARGET_TYPE_EQ)) || + (K == (TARGET_TYPE_PROC_CHIP | TARGET_TYPE_CORE))) && ((T == TARGET_TYPE_EQ) || (T == TARGET_TYPE_EX) || (T == TARGET_TYPE_PROC_CHIP) || @@ -299,23 +225,23 @@ namespace fapi2 if(TARGET_TYPE_PERV == T) // EQ/EC/MCBIST/PERV ===> PERV { - return this->iv_handle; + return static_cast(this->iv_handle); } if(TARGET_TYPE_PROC_CHIP == T) // EQ/EC/EX/MCBIST/PERV ===> PROC { - return G_vec_targets[CHIP_TARGET_OFFSET]; + return static_cast(G_vec_targets[CHIP_TARGET_OFFSET]); } if((TARGET_TYPE_EQ == T) && (TARGET_TYPE_CORE == K)) // EC ===> EQ { - return G_vec_targets[(getTargetNumber() / CORES_PER_QUAD) + EQ_TARGET_OFFSET]; + return static_cast(G_vec_targets[(getTargetNumber() / CORES_PER_QUAD) + EQ_TARGET_OFFSET]); } if((TARGET_TYPE_EQ == T) && (TARGET_TYPE_EX == K)) // EX ===> EQ { - return G_vec_targets[(getTargetNumber() / EX_PER_QUAD) + EQ_TARGET_OFFSET]; + return static_cast(G_vec_targets[(getTargetNumber() / EX_PER_QUAD) + EQ_TARGET_OFFSET]); } if(TARGET_TYPE_EX == T) // EC ===> EX { - return G_vec_targets[(getTargetNumber() / CORES_PER_EX) + EX_TARGET_OFFSET]; + return static_cast(G_vec_targets[(getTargetNumber() / CORES_PER_EX) + EX_TARGET_OFFSET]); } } @@ -324,187 +250,75 @@ namespace fapi2 /// @tparam V The plat target handle type /// @tparam T The type of child /// @param[in] i_state The desired TargetState of the children - /// @return std::vector > a vector of present/functional + /// @return std::vector > a vector of present/functional /// children /// @warning The children are returned in order, ex child[0] is /// std::vector[0] template template - std::vector> + std::vector> Target::getChildren(const TargetState i_state) const { - static_assert(((K == TARGET_TYPE_EQ) || (K == TARGET_TYPE_EX)) && - ((T == TARGET_TYPE_EX) || (T == TARGET_TYPE_CORE)), - "Invalid parent/child passed to getChildren"); + constexpr TargetType L = static_cast(K & ~(TARGET_TYPE_PROC_CHIP)); + constexpr plat_target_type_t P = fapiTargetTypeToPlatTargetType(); + + static_assert(sizeof(Target) == sizeof(plat_target_handle_t), + "Sizes of plat target and FAPI target must match"); + + static_assert(((L == TARGET_TYPE_EQ) || (L == TARGET_TYPE_EX) || (K == TARGET_TYPE_PROC_CHIP)), + "Invalid parent passed to getChildren"); // valid children for EQ // EQ -> CORE // EQ -> EX - static_assert(!((K == fapi2::TARGET_TYPE_EQ) && + static_assert(!((L == fapi2::TARGET_TYPE_EQ) && (T != fapi2::TARGET_TYPE_CORE) && (T != fapi2::TARGET_TYPE_EX)), "improper child of fapi2::TARGET_TYPE_EQ"); // valid children for EX // EX -> CORE - static_assert(!((K == fapi2::TARGET_TYPE_EX) && + static_assert(!((L == fapi2::TARGET_TYPE_EX) && (T != fapi2::TARGET_TYPE_CORE)), "improper child of fapi2::TARGET_TYPE_EX"); - std::vector > l_children; - uint32_t l_childPerChiplet = 0; - uint32_t l_childTargetOffset = 0; - - // EQ ==> EX - if((K == TARGET_TYPE_EQ) && (T == TARGET_TYPE_EX)) - { - l_childPerChiplet = EX_PER_QUAD; - l_childTargetOffset = EX_TARGET_OFFSET; - } - - // EQ ==> EC - if((K == TARGET_TYPE_EQ) && (T == TARGET_TYPE_CORE)) - { - l_childPerChiplet = CORES_PER_QUAD; - l_childTargetOffset = CORE_TARGET_OFFSET; - } - - // EX ==> EC - if((K == TARGET_TYPE_EX) && (T == TARGET_TYPE_CORE)) - { - l_childPerChiplet = CORES_PER_EX; - l_childTargetOffset = CORE_TARGET_OFFSET; - } - - for(uint32_t i = 0; i < l_childPerChiplet; ++i) - { - Target *l_temp = reinterpret_cast< Target* >(&G_vec_targets.at((getTargetNumber() * l_childPerChiplet) + l_childTargetOffset + i)); - switch (i_state) - { - case TARGET_STATE_PRESENT: - if ((*l_temp).getPresent()) - { - l_children.push_back((*l_temp)); - } - break; - case TARGET_STATE_FUNCTIONAL: - if ((*l_temp).getFunctional()) - { - l_children.push_back((*l_temp)); - } - break; - default: - assert(false); - } - } - - return l_children; - } - - /// - /// @brief Get this target's children - specialization for PROC_CHIP - /// @tparam T The type of child - /// @param[in] i_state The desired TargetState of the children - /// @return std::vector > a vector of present/functional - /// children - /// - template<> - template< TargetType T> - std::vector > - Target::getChildren(const TargetState i_state) const - { - std::vector::iterator l_iter; - std::vector > l_children; - constexpr plat_target_type_t P = fapiTargetTypeToPlatTargetType(); - - for (l_iter = G_vec_targets.begin(); l_iter != G_vec_targets.end(); ++l_iter) - { - Target * l_temp = reinterpret_cast< Target* >(l_iter); - if (((*l_temp).getTargetType() & P) == P) - { - switch (i_state) - { - case TARGET_STATE_PRESENT: - if ((*l_temp).getPresent()) - { - l_children.push_back((*l_temp)); - } - break; - case TARGET_STATE_FUNCTIONAL: - if ((*l_temp).getFunctional()) - { - l_children.push_back((*l_temp)); - } - break; - default: - assert(false); - } - } - } + std::vector > l_children; + static_cast(get()).getChildren(K, T, P, i_state, reinterpret_cast&>(l_children)); return l_children; } // Specialization of getChildren, filtered for the chip target template template - std::vector > + std::vector > Target::getChildren(const TargetFilter i_filter, const TargetState i_state) const { + static_assert(sizeof(Target) == sizeof(plat_target_handle_t), + "Sizes of plat target and FAPI target must match"); + static_assert((K == TARGET_TYPE_PROC_CHIP), "Parent target must be the proc chip"); static_assert((T == TARGET_TYPE_EQ) || (T == TARGET_TYPE_CORE) || (T == TARGET_TYPE_PERV) || (T == TARGET_TYPE_MCBIST), "Child target type must be a pervasive chiplet"); std::vector > l_children; - static const uint64_t mask = 1; - - // Walk the bits in the input target filter. For every bit, at - // position x, that is set, x can be used as an index into our global - // target vector (indexed by chiplet number) - for (uint32_t l_idx = 0; - l_idx < sizeof(TargetFilter) * 8; - ++l_idx) - { - if (i_filter & (mask << (((sizeof(TargetFilter)*8)-1) - l_idx))) - { - plat_target_handle_t l_targetHandle = G_vec_targets.at(l_idx + NEST_GROUP1_CHIPLET_OFFSET); - - if(l_targetHandle.fields.type & PPE_TARGET_TYPE_PERV) // Can be an assertion? - { - switch (i_state) - { - case TARGET_STATE_PRESENT: - if(l_targetHandle.fields.present) - { - l_children.push_back(l_targetHandle); - } - break; - case TARGET_STATE_FUNCTIONAL: - if(l_targetHandle.fields.functional) - { - l_children.push_back(l_targetHandle); - } - break; - default: - break; - } - } - } - } - return l_children; + + (static_cast(get())).getChildren(i_filter, i_state, reinterpret_cast&>(l_children)); + + return l_children; } /// /// @brief Get the target at the other end of a bus - dimm included /// @tparam T The type of the parent /// @param[in] i_state The desired TargetState of the children - /// @return Target a target representing the thing on the other end + /// @return Target a target representing the thing on the other end /// @note Can be easily changed to a vector if needed /// template template - inline Target + inline Target Target::getOtherEnd(const TargetState i_state) const { // static_assert( false, "getOtherEnd() is not supported on PPE platforms"); @@ -533,15 +347,15 @@ namespace fapi2 /// @post The contents of the buffer is replaced with the string /// representation of the target /// - template< TargetType T > - inline void toString(const Target& i_target, char* i_buffer, size_t i_bsize) + template< TargetType T, typename V > + inline void toString(const Target& i_target, char* i_buffer, size_t i_bsize) { snprintf(i_buffer, i_bsize, "Target 0x%lx/0x%x", i_target.get(), T); } - template + template __attribute__((always_inline)) - inline uint32_t getEffectiveAddress(const Target &i_target, + inline uint32_t getEffectiveAddress(const Target &i_target, const uint32_t i_addr) { ScomAddr l_addr = i_addr; @@ -590,15 +404,15 @@ namespace fapi2 /// @brief Return the string interpretation of this target /// @tparam T The type of the target /// @tparam B The type of the buffer - /// @param[in] A pointer to the Target + /// @param[in] A pointer to the Target /// @param[in] i_buffer buffer to write in to /// @param[in] i_bsize size of the buffer /// @return void /// @post The contents of the buffer is replaced with the string /// representation of the target /// - template< TargetType T > - inline void toString(const Target* i_target, char* i_buffer, size_t i_bsize) + template< TargetType T, typename V > + inline void toString(const Target* i_target, char* i_buffer, size_t i_bsize) { snprintf(i_buffer, i_bsize, "Target 0x%lx/0x%x", i_target->get(), T); } @@ -608,13 +422,13 @@ namespace fapi2 /// @tparam T The type of the target /// @param[in] Ordinal representing the ordinal number of /// the desired target - /// @return Target the target requested + /// @return Target the target requested /// - template - inline Target getTarget(uint64_t Ordinal) + template + inline Target getTarget(uint64_t Ordinal) { // For testing - return Target(Ordinal); + return Target(Ordinal); } } -- cgit v1.2.1