summaryrefslogtreecommitdiffstats
path: root/hwpf
diff options
context:
space:
mode:
authorSachin Gupta <sgupta2m@in.ibm.com>2015-07-14 05:18:40 -0500
committerJennifer A. Stofer <stofer@us.ibm.com>2015-07-28 15:21:17 -0500
commitd553cfa7b58b4529e72557b219b87319c11da043 (patch)
tree153ee4403caa10105a1e5280c4916076f659b183 /hwpf
parent8fd7df0b85039d5dc5f8a23f0d80cbce7d30a600 (diff)
downloadtalos-sbe-d553cfa7b58b4529e72557b219b87319c11da043.tar.gz
talos-sbe-d553cfa7b58b4529e72557b219b87319c11da043.zip
Add SBE support for per directory error XML files
- Added parseErrorInfo.pl Change-Id: I263797070f09d0b869f3de52916049574d272cb6 Reviewed-on: http://gfw160.aus.stglabs.ibm.com:8080/gerrit/18819 Reviewed-by: Jennifer A. Stofer <stofer@us.ibm.com> Tested-by: Jennifer A. Stofer <stofer@us.ibm.com>
Diffstat (limited to 'hwpf')
-rw-r--r--hwpf/plat/include/buffer.H220
-rwxr-xr-xhwpf/plat/include/buffer_base.H331
-rw-r--r--hwpf/plat/include/buffer_parameters.H19
-rw-r--r--hwpf/plat/include/buffer_traits.H8
-rw-r--r--hwpf/plat/include/utils.H12
5 files changed, 508 insertions, 82 deletions
diff --git a/hwpf/plat/include/buffer.H b/hwpf/plat/include/buffer.H
index 9e863c3b..62e7e7cf 100644
--- a/hwpf/plat/include/buffer.H
+++ b/hwpf/plat/include/buffer.H
@@ -36,11 +36,11 @@
namespace fapi2
{
- /// @brief Class representing a FAPI buffer<T>
- /// @tparam T, the integral type of the buffer (uint16_t, uint64_t, etc.)
- template <typename T, typename TT = bufferTraits<T> >
- class buffer
- {
+/// @brief Class representing a FAPI buffer<T>
+/// @tparam T, the integral type of the buffer (uint16_t, uint64_t, etc.)
+template <typename T, typename TT = bufferTraits<T> >
+class buffer
+{
public:
/// Shortcut typedef to get to our traits class
typedef typename TT::bits_type bits_type;
@@ -52,40 +52,54 @@ namespace fapi2
///
inline buffer(T i_value = 0):
iv_data(i_value)
- {
- }
+ {
+ }
~buffer(void) = default;
-#if !defined(DOXYGEN) && defined(FAPI2_DEBUG)
+ #if !defined(DOXYGEN) && defined(FAPI2_DEBUG)
/// @brief Print the contents of the buffer to stdout
inline void print(void) const
- { TT::print(iv_data); }
-#endif
+ {
+ TT::print(iv_data);
+ }
+ #endif
///
/// @brief Get the contents of the buffer
/// @return The contents of the buffer
///
- inline operator T() const { return iv_data; }
+ inline operator T() const
+ {
+ return iv_data;
+ }
///
/// @brief Get the contents of the buffer
/// @return The contents of the buffer
///
- inline operator T&() { return iv_data; }
+ inline operator T&()
+ {
+ return iv_data;
+ }
///
/// @brief Get the contents of the buffer
/// @return The contents of the buffer
///
- inline T& operator()(void) { return iv_data; }
+ inline T& operator()(void)
+ {
+ return iv_data;
+ }
///
/// @brief Get the contents of the buffer
/// @return Reference to the contents of the buffer
///
- inline const T& operator()(void) const { return iv_data; }
+ inline const T& operator()(void) const
+ {
+ return iv_data;
+ }
/// @name Buffer Manipulation Functions
///@{
@@ -118,11 +132,14 @@ namespace fapi2
// Create mask if part of this byte is not in the valid part of the buffer,
// Shift it left by the amount of unused bits,
// Clear the unused bits
- if (((i_offset + 1) == length) && (bit_length % bits_in_value)) {
- i_value &= parameterTraits<OT>::mask() << ((bits_in_value * length) - bit_length);
+ if (((i_offset + 1) == length) && (bit_length % bits_in_value))
+ {
+ i_value &= parameterTraits<OT>::mask() << ((bits_in_value * length) -
+ bit_length);
}
- parameterTraits<OT>::template write_element<typename TT::unit_type>(TT::get_address(iv_data), i_value, i_offset);
+ parameterTraits<OT>::template write_element<typename TT::unit_type>
+ (TT::get_address(iv_data), i_value, i_offset);
return FAPI2_RC_SUCCESS;
}
@@ -134,7 +151,9 @@ namespace fapi2
/// @return Length in bits
///
inline constexpr uint32_t getBitLength(void) const
- { return TT::bit_length(iv_data); }
+ {
+ return TT::bit_length(iv_data);
+ }
///
/// @brief Return the length of the buffer in OT units
@@ -167,7 +186,8 @@ namespace fapi2
// This would be a candidate for a fast_mask (see variable_buffer) but
// we'd need tables for all the integral types which maybe we need to
// do ...
- iv_data |= (T(~0) >> (TT::bits_per_unit() - C)) << (TT::bits_per_unit() - B - C);
+ iv_data |= (T(~0) >> (TT::bits_per_unit() - C)) << (TT::bits_per_unit() - B -
+ C);
return *this;
}
@@ -178,14 +198,16 @@ namespace fapi2
/// @note 0 is left-most
/// @return FAPI2_RC_SUCCESS if OK
///
- inline fapi2::ReturnCode setBit(const bits_type& i_bit, const bits_type& i_count = 1)
+ inline fapi2::ReturnCode setBit(const bits_type& i_bit,
+ const bits_type& i_count = 1)
{
if ((i_count + i_bit - 1) >= TT::bits_per_unit())
{
return FAPI2_RC_INVALID_PARAMETER;
}
- iv_data |= (T(~0) >> (TT::bits_per_unit() - i_count)) << (TT::bits_per_unit() - i_bit - i_count);
+ iv_data |= (T(~0) >> (TT::bits_per_unit() - i_count)) <<
+ (TT::bits_per_unit() - i_bit - i_count);
return FAPI2_RC_SUCCESS;
}
@@ -216,7 +238,8 @@ namespace fapi2
/// @note 0 is left-most
/// @return FAPI2_RC_SUCCESS if OK
///
- inline fapi2::ReturnCode clearBit(const bits_type& i_bit, const bits_type& i_count = 1)
+ inline fapi2::ReturnCode clearBit(const bits_type& i_bit,
+ const bits_type& i_count = 1)
{
if ((i_count + i_bit - 1) >= TT::bits_per_unit())
{
@@ -282,9 +305,9 @@ namespace fapi2
///
template< bits_type B, bits_type C = 1>
inline bool getBit(void) const
- {
- return buffer<T>().setBit<B, C>() & iv_data;
- }
+ {
+ return buffer<T>().setBit<B, C>() & iv_data;
+ }
///
/// @brief Set and entire buffer to X's
@@ -294,25 +317,31 @@ namespace fapi2
///
template< uint8_t X >
inline buffer& flush(void)
- {
- static_assert( (X == 1) || (X == 0), "bad argument to flush" );
- (0 == X) ? TT::clear(iv_data) : TT::set(iv_data);
- return *this;
- }
+ {
+ static_assert( (X == 1) || (X == 0), "bad argument to flush" );
+ (0 == X) ? TT::clear(iv_data) : TT::set(iv_data);
+ return *this;
+ }
///
/// @brief Invert entire buffer
/// @return buffer_base&, Useful for method chaining
///
inline buffer& invert(void)
- { TT::invert(iv_data); return *this; }
+ {
+ TT::invert(iv_data);
+ return *this;
+ }
///
/// @brief Bit reverse entire buffer
/// @return buffer_base&, Useful for method chaining
///
inline buffer& reverse(void)
- { TT::reverse(iv_data); return *this; }
+ {
+ TT::reverse(iv_data);
+ return *this;
+ }
///@}
@@ -324,7 +353,10 @@ namespace fapi2
/// @brief Get a pointer to the buffer bits
/// @return Pointer to the buffer itself
///
- inline T* pointer(void) { return &iv_data; }
+ inline T* pointer(void)
+ {
+ return &iv_data;
+ }
// Note: Many (all?) of these are not needed and the compiler complains
// as the cast to T yields a better operator. There are here mainly for
@@ -333,86 +365,86 @@ namespace fapi2
///
/// @brief operator>>()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator>>(bits_type i_shiftnum);
-#endif
+ #endif
///
/// @brief operator<<()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator<<(bits_type i_shiftnum);
-#endif
+ #endif
///
/// @brief operator+()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator+(const T& rhs);
-#endif
+ #endif
///
/// @brief operator+=()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator+=(const T& rhs);
-#endif
+ #endif
///
/// @brief operator|=()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator|=(const T& rhs);
-#endif
+ #endif
///
/// @brief operator&=()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator&=(const T& rhs);
-#endif
+ #endif
///
/// @brief operator|()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator|(const T& rhs);
-#endif
+ #endif
///
/// @brief operator&()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator&(const T& rhs);
-#endif
+ #endif
///
/// @brief operator^=()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator^=(const T& rhs);
-#endif
+ #endif
///
/// @brief operator~()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline buffer<T>& operator~(const T& rhs) const;
-#endif
+ #endif
///
/// @brief operator==()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline bool operator==(const T& rhs) const;
-#endif
+ #endif
///
/// @brief operator!=()
///
-#ifdef DOXYGEN
+ #ifdef DOXYGEN
inline bool operator!=(const T& rhs) const;
-#endif
+ #endif
///
/// @brief Copy part of a OT into the DataBuffer
@@ -444,15 +476,19 @@ namespace fapi2
uint64_t source = static_cast<uint64_t>(i_datain);
const uint64_t target = static_cast<uint64_t>(iv_data);
- const bits_type source_start = parameterTraits<uint64_t>::bit_length - (source_length - SS);
- const bits_type target_start = parameterTraits<uint64_t>::bit_length - (target_length - TS);
+ const bits_type source_start = parameterTraits<uint64_t>::bit_length() -
+ (source_length - SS);
+ const bits_type target_start = parameterTraits<uint64_t>::bit_length() -
+ (target_length - TS);
// Get mask value for Target buffer
// Note: Need "& 0UL" because bit shift left for Target buffer doesn't roll off
- uint64_t mask = ((~0UL << (parameterTraits<uint64_t>::bit_length - L)) & ~0UL) >> target_start;
+ uint64_t mask = ((~0UL << (parameterTraits<uint64_t>::bit_length() - L)) & ~0UL)
+ >> target_start;
// Align the source to the target. Make things signed so we know which way to shift.
int32_t shift = source_start - target_start;
+
if (shift > 0)
{
source <<= shift;
@@ -514,15 +550,19 @@ namespace fapi2
uint64_t source = static_cast<uint64_t>(i_datain);
const uint64_t target = static_cast<uint64_t>(iv_data);
- const bits_type source_start = parameterTraits<uint64_t>::bit_length - (source_length - i_sourceStart);
- const bits_type target_start = parameterTraits<uint64_t>::bit_length - (target_length - i_targetStart);
+ const bits_type source_start = parameterTraits<uint64_t>::bit_length() -
+ (source_length - i_sourceStart);
+ const bits_type target_start = parameterTraits<uint64_t>::bit_length() -
+ (target_length - i_targetStart);
// Get mask value for Target buffer
// Note: Need "& 0UL" because bit shift left for Target buffer doesn't roll off
- uint64_t mask = ((~0UL << (parameterTraits<uint64_t>::bit_length - i_len)) & ~0UL) >> target_start;
+ uint64_t mask = ((~0UL << (parameterTraits<uint64_t>::bit_length() - i_len)) &
+ ~0UL) >> target_start;
// Align the source to the target. Make things signed so we know which way to shift.
int32_t shift = source_start - target_start;
+
if (shift > 0)
{
source <<= shift;
@@ -573,7 +613,8 @@ namespace fapi2
/// @note Data is assumed to be aligned on the word boundary of L
///
template<typename OT>
- fapi2::ReturnCode insertFromRight(const OT i_datain, const bits_type i_targetStart,
+ fapi2::ReturnCode insertFromRight(const OT i_datain,
+ const bits_type i_targetStart,
const bits_type i_len)
{
// Error if input data don't make sense
@@ -595,7 +636,28 @@ namespace fapi2
return FAPI2_RC_INVALID_PARAMETER;
}
- return this->insert(i_datain, i_targetStart, i_len, parameterTraits<OT>::bit_length() - i_len);
+ return this->insert(i_datain, i_targetStart, i_len,
+ parameterTraits<OT>::bit_length() - i_len);
+ }
+
+ ///
+ /// @brief Copy data from this buffer into an OT
+ /// @tparam SS Start bit in source
+ /// @tparam L Length of bits to insert
+ /// @tparam TS Start bit to insert into (target start)
+ /// @tparam OT the type of the outgoing (target)
+ /// @param[out] o_out OT to copy into - data is placed left aligned
+ /// @return const buffer& Useful for method chaining
+ ///
+ template<bits_type SS, bits_type L, bits_type TS = 0, typename OT>
+ inline const buffer& extract(OT& o_out) const
+ {
+ // Extraction is just an insert into o_out
+
+ buffer<OT> out(o_out);
+ out.insert<TS, L, SS>(iv_data);
+ o_out = out;
+ return *this;
}
///
@@ -629,12 +691,14 @@ namespace fapi2
///
template<typename OT>
fapi2::ReturnCode extract(OT& o_out, const bits_type i_sourceStart,
- const bits_type i_len, const bits_type i_targetStart = 0)
+ const bits_type i_len, const bits_type i_targetStart = 0) const
{
// Extraction is just an insert into o_out
buffer<OT> out(o_out);
- if (out.insert(iv_data, i_targetStart, i_len, i_sourceStart) != FAPI2_RC_SUCCESS)
+
+ if (out.insert(iv_data, i_targetStart, i_len,
+ i_sourceStart) != FAPI2_RC_SUCCESS)
{
return FAPI2_RC_INVALID_PARAMETER;
}
@@ -649,6 +713,21 @@ namespace fapi2
/// @tparam L Length of bits to extract
/// @tparam OT the type of the outgoing (target)
/// @param[out] o_out OT to copy into - data is placed right aligned
+ /// @return const buffer& Useful for method chaining
+ ///
+ template<bits_type SS, bits_type L, typename OT>
+ inline const buffer& extractToRight(OT& o_out) const
+ {
+ extract<SS, L, parameterTraits<OT>::bit_length() - L>(o_out);
+ return *this;
+ }
+
+ ///
+ /// @brief Copy data from this buffer into an OT and right justify
+ /// @tparam SS Start bit to insert into (source start)
+ /// @tparam L Length of bits to extract
+ /// @tparam OT the type of the outgoing (target)
+ /// @param[out] o_out OT to copy into - data is placed right aligned
/// @return buffer& Useful for method chaining
///
template<bits_type SS, bits_type L, typename OT>
@@ -668,9 +747,10 @@ namespace fapi2
///
template<typename OT>
fapi2::ReturnCode extractToRight(OT& o_out, const bits_type i_sourceStart,
- const bits_type i_len)
+ const bits_type i_len) const
{
- return extract(o_out, i_sourceStart, i_len, parameterTraits<OT>::bit_length() - i_len);
+ return extract(o_out, i_sourceStart, i_len,
+ parameterTraits<OT>::bit_length() - i_len);
}
///@}
@@ -678,7 +758,7 @@ namespace fapi2
private:
/// The contents of the buffer
T iv_data;
- };
+};
}
#endif
diff --git a/hwpf/plat/include/buffer_base.H b/hwpf/plat/include/buffer_base.H
new file mode 100755
index 00000000..a6e8c4ad
--- /dev/null
+++ b/hwpf/plat/include/buffer_base.H
@@ -0,0 +1,331 @@
+/* IBM_PROLOG_BEGIN_TAG */
+/* This is an automatically generated prolog. */
+/* */
+/* $Source: $ */
+/* */
+/* OpenPOWER HostBoot Project */
+/* */
+/* Contributors Listed Below - COPYRIGHT 2012,2014 */
+/* [+] International Business Machines Corp. */
+/* */
+/* */
+/* Licensed under the Apache License, Version 2.0 (the "License"); */
+/* you may not use this file except in compliance with the License. */
+/* You may obtain a copy of the License at */
+/* */
+/* http://www.apache.org/licenses/LICENSE-2.0 */
+/* */
+/* Unless required by applicable law or agreed to in writing, software */
+/* distributed under the License is distributed on an "AS IS" BASIS, */
+/* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or */
+/* implied. See the License for the specific language governing */
+/* permissions and limitations under the License. */
+/* */
+/* IBM_PROLOG_END_TAG */
+/**
+ * @file buffer_base.H
+ * @brief definitions for fapi2 buffer base class
+ */
+
+#ifndef __FAPI2_BUFFER_BASE__
+#define __FAPI2_BUFFER_BASE__
+
+#include <stdint.h>
+#include <initializer_list>
+#include <error_scope.H>
+#include <buffer_parameters.H>
+#include <buffer_traits.H>
+#include <return_code.H>
+
+namespace fapi2
+{
+ /// @brief Base class for buffers and variable buffers
+ /// @tparam T is the type of iv_data (std::vector, etc)
+ /// @tparam TT is the template trait, defaults to the trait for T
+ ///
+ /// Buffers can be of two styles; buffers made from an integral type and
+ /// buffers made from a container. Integral type buffers, while limited
+ /// in size, can be tightly controlled via the compiler by using c++
+ /// templates.
+ ///
+ /// C++ templates allow for very explicit control, but yield a
+ /// syntax different than the FAPI 1.x functional interface. For example,
+ /// a fapi2::buffer is defined as having a type:
+ /// @code
+ /// fapi2::buffer<uint64_t> new_buffer;
+ /// @endcode
+ /// defines a buffer with exactly 64 bits, and can be manipulated by the
+ /// compiler as a single intrgral value. These implementations result
+ /// in concise instruction streams, and a platform may choose to implement
+ /// all or some or none of the integral buffer types.
+ ///
+ /// Buffers which have containers as their underlying implementation
+ /// are found in the class fapi2::variable_buffer. variable_buffer is little
+ /// more than
+ /// @code
+ /// fapi2::buffer<fapi2::bits_container>
+ /// @endcode
+ /// where bits_container is the typedef of the underlying container (a
+ /// vector of uint32_t, for example)
+ ///
+ /// Examples:<br>
+ ///
+ /// * Simple uint64_t buffer
+ /// @code
+ /// const uint32_t x = 2;
+ ///
+ /// // this data buffer will contain data in a uint64_t type
+ /// fapi2::buffer<uint64_t> data;
+ ///
+ /// // Set using the template and a constant
+ /// data.setBit<x>();
+ ///
+ /// // Set using the template and a value
+ /// data.setBit<3>();
+ ///
+ /// // Set using the function interface, and a value
+ /// data.setBit(1);
+ ///
+ /// // compiler gets smart.
+ /// // movabs $0x7000000000000000,%rsi
+ /// @endcode
+ ///
+ /// * variable_buffer, same thing
+ /// @code
+ ///
+ /// const uint32_t x = 2;
+ ///
+ /// // Note: only 15 bits long
+ /// fapi2::variable_buffer data(15);
+ ///
+ ///
+ /// data.setBit(x);
+ /// data.setBit(3);
+ /// data.setBit(1);
+ /// @endcode
+ ///
+ /// * method chaining
+ /// Buffers support method chaining. So, rather than
+ /// this
+ /// @code
+ /// buffer<T> mask;
+ /// mask.setBit<B>();
+ /// mask.invert();
+ /// my_buffer &= mask;
+ /// @endcode
+ /// You can do
+ /// @code
+ /// my_buffer &= buffer<T>().setBit<B>.invert();
+ /// @endcode
+ ///
+ /// * buffer operations
+ /// @code
+ ///
+ /// // An 8 bit buffer, initialized with a value
+ /// fapi2::buffer<uint8_t> eight_bits = 0xAA;
+ /// fapi2::buffer<uint8_t> another_eight;
+ /// fapi2::buffer<uint16_t> sixteen_bits;
+ ///
+ /// // You can't assign an 8 bit buffer to a 16 bit buffer.
+ /// sixteen_bits = eight_bits; ERROR
+ ///
+ /// // But you can assign buffers of the same type
+ /// another_eight = eight_bits;
+ ///
+ /// // You can assign constants (or other known values) directly:
+ /// sixteen_bits = 0xAABB;
+ /// @endcode
+ ///
+ /// * Variable buffer operations
+ ///
+ /// @code
+ /// fapi2::variable_buffer data(16);
+ ///
+ /// // Very large buffers can be initialized rather than set bit by bit.
+ /// const fapi2::variable_buffer bit_settings_known(
+ /// {0xFFFF0000, 0xAABBF0F0,
+ /// 0xFFFF0000, 0xAABBF0F0,
+ /// 0xFFFF0000, 0xAABBF0F0,});
+ ///
+ /// // Assignment will expand or shrink the size automatically.
+ /// data = bit_settings_known;
+ ///
+ /// // You can assign directly to the buffer:
+ /// fapi2::variable_buffer other_bits;
+ /// const fapi2::container_unit x = 0xFF00AA55;
+ /// other_bits = {x, 0xDEADBEEF};
+ /// @endcode
+ ///
+ template <typename T, typename TT = bufferTraits<T> >
+ class buffer_base
+ {
+
+ public:
+
+ /// Shortcut typedef to get to our traits class
+ typedef typename TT::bits_type bits_type;
+ /// Shortcut typedef to get to our traits class
+ typedef typename TT::unit_type unit_type;
+
+ ///
+ /// @brief Default constructor
+ /// @note iv_data will get the "default" construction, which is
+ /// correct - 0 for integral types, an empty container for the others.
+ ///
+ buffer_base(void):
+ iv_data()
+ {}
+
+ virtual ~buffer_base(void)
+ {}
+
+#ifndef DOXYGEN
+ /// @brief Print the contents of the buffer to stdout
+ inline void print(void) const
+ { TT::print(iv_data); }
+#endif
+ ///
+ /// @brief Get the contents of the buffer
+ /// @return The contents of the buffer
+ ///
+ inline operator T() const { return iv_data; }
+
+ ///
+ /// @brief Get the contents of the buffer
+ /// @return The contents of the buffer
+ ///
+ inline operator T&() { return iv_data; }
+
+ ///
+ /// @brief Get the contents of the buffer
+ /// @return The contents of the buffer
+ ///
+ inline T& operator()(void) { return iv_data; }
+
+ ///
+ /// @brief Get the contents of the buffer
+ /// @return Reference to the contents of the buffer
+ ///
+ inline const T& operator()(void) const { return iv_data; }
+
+ ///
+ /// @brief Get a pointer to the buffer bits
+ /// @return Pointer to the buffer itself
+ ///
+ inline T* pointer(void) { return &iv_data; }
+
+ /// @name Buffer Manipulation Functions
+ ///@{
+
+ ///
+ /// @brief Set an OT of data in buffer
+ /// @param[in] i_value sizeof(OT) bits of data
+ /// @param[in] i_offset Start OT (start word, for example) in buffer
+ /// - defaults to 0 (will by default write the left most element)
+ /// @return FAPI2_RC_SUCCESS on success, FAPI2_RC_OVERFLOW otherwise
+ /// @note This is is only available for integral types. To set a
+ /// variable_buffer into a variable_buffer, use insert()
+ ///
+ template< typename OT>
+ inline fapi2::ReturnCode set(OT i_value, const bits_type i_offset = 0)
+ {
+ // Compile time check to make sure OT isn't a variable buffer
+ static_assert( !std::is_same<bits_container, OT>::value,
+ "Can't use a variable_buffer as input to set()" );
+
+ //
+ // There's a gotcha in here. size<OT>() returns the size in the buffer
+ // in OT units *rounded up*. This is the actual size of the buffer, not
+ // the perceived size of a variable_buffer. This should be OK however,
+ // as what we're trying to prevent is overflow, which this should do.
+ //
+ const uint32_t length = TT:: template size<OT>(iv_data);
+ static const bits_type bits_in_value = parameterTraits<OT>::bit_length;
+ const bits_type bit_length = TT::bit_length(iv_data);
+
+ if (i_offset >= length)
+ {
+ return FAPI2_RC_OVERFLOW;
+ }
+
+ // Create mask if part of this byte is not in the valid part of the buffer,
+ // Shift it left by the amount of unused bits,
+ // Clear the unused bits
+ if (((i_offset + 1) == length) && (bit_length % bits_in_value)) {
+ i_value &= parameterTraits<OT>::mask << ((bits_in_value * length) - bit_length);
+ }
+
+ parameterTraits<OT>::template write_element<unit_type>(TT::get_address(iv_data), i_value, i_offset);
+ return FAPI2_RC_SUCCESS;
+ }
+
+ ///
+ /// @brief Set and entire buffer to X's
+ /// @tparam X {0,1} depending if you want to clear (0)
+ /// or fill (1) a buffer
+ ///
+ template< uint8_t X >
+ inline void flush(void)
+ {
+ static_assert( (X == 1) || (X == 0), "bad argument to flush" );
+ (0 == X) ? TT::clear(iv_data) : TT::set(iv_data);
+ }
+
+ ///
+ /// @brief Invert entire buffer
+ /// @return buffer_base&, Useful for method chaining
+ ///
+ inline buffer_base& invert(void)
+ { TT::invert(iv_data); return *this; }
+
+ ///
+ /// @brief Bit reverse entire buffer
+ /// @return buffer_base&, Useful for method chaining
+ ///
+ inline buffer_base& reverse(void)
+ { TT::reverse(iv_data); return *this; }
+
+ //@}
+ protected:
+
+ ///
+ /// @brief Variable buffer constructor
+ /// @param[in] i_value number of *bits* (sizeof(container_units) * 8)
+ /// needed. Meaningless for integral types and thus protected.
+ ///
+ buffer_base(bits_type i_value);
+
+ ///
+ /// @brief Variable buffer construct from a list
+ /// @param[in] i_value an initializer list to initialize the container.
+ /// Meaningless for integral types and thus protected
+ ///
+ buffer_base(std::initializer_list<unit_type> i_value);
+
+ ///
+ /// @brief Clear the buffer
+ ///
+ inline void clear(void)
+ { TT::clear(iv_data); }
+
+ /// The contents of the buffer
+ T iv_data;
+ };
+
+ template <typename T, typename TT>
+ inline buffer_base<T, TT>::buffer_base(bits_type i_value):
+ iv_data( std::max(bits_type(1),
+ bits_type(i_value / 8 / sizeof(bits_type))))
+ {
+ }
+
+ template <typename T, typename TT>
+ inline buffer_base<T, TT>::buffer_base(std::initializer_list<unit_type> i_value):
+ iv_data(i_value)
+ {
+ }
+};
+
+
+
+#endif
diff --git a/hwpf/plat/include/buffer_parameters.H b/hwpf/plat/include/buffer_parameters.H
index 3dc41b26..2a6e6100 100644
--- a/hwpf/plat/include/buffer_parameters.H
+++ b/hwpf/plat/include/buffer_parameters.H
@@ -41,12 +41,17 @@ namespace fapi2
class parameterTraits
{
public:
- enum
- {
- mask = T(~0),
- bit_length = sizeof(T) * 8,
- byte_length = sizeof(T),
- };
+ // Why constexpr functions? Enums are hard to do math on, and
+ // static const doesn't work without -O1 (or greater.) That might
+ // be a bug in g++ but this works just the same.
+ constexpr static T mask(void)
+ { return T(~0); }
+
+ constexpr static uint32_t byte_length(void)
+ { return sizeof(T); }
+
+ constexpr static uint32_t bit_length(void)
+ { return sizeof(T) * 8; }
template<typename U>
inline static void write_element(void* i_data, T i_value, uint32_t i_offset)
@@ -60,6 +65,6 @@ namespace fapi2
}
};
/// @endcond
-};
+}
#endif
diff --git a/hwpf/plat/include/buffer_traits.H b/hwpf/plat/include/buffer_traits.H
index 8f42ce9e..7cab81ff 100644
--- a/hwpf/plat/include/buffer_traits.H
+++ b/hwpf/plat/include/buffer_traits.H
@@ -91,8 +91,8 @@ namespace fapi2
constexpr static B size(const T& i_buffer)
{
return (bit_length(i_buffer) +
- (parameterTraits<E>::bit_length - 1)) /
- parameterTraits<E>::bit_length;
+ (parameterTraits<E>::bit_length() - 1)) /
+ parameterTraits<E>::bit_length();
}
///
@@ -182,8 +182,8 @@ namespace fapi2
constexpr static uint32_t size(const bits_container& i_buffer)
{
return (bit_length(i_buffer) +
- (parameterTraits<E>::bit_length - 1)) /
- parameterTraits<E>::bit_length;
+ (parameterTraits<E>::bit_length() - 1)) /
+ parameterTraits<E>::bit_length();
}
///
diff --git a/hwpf/plat/include/utils.H b/hwpf/plat/include/utils.H
index 216656c8..69e84d20 100644
--- a/hwpf/plat/include/utils.H
+++ b/hwpf/plat/include/utils.H
@@ -66,6 +66,16 @@ uint64_t revle64(uint64_t i_x);
#endif
-
+namespace fapi2
+{
+ /// @brief Delay this thread.
+ /// @param[in] i_nanoSeconds nanoseconds to sleep
+ /// @param[in] i_simCycles count of Awan cycles to advance
+ /// @return ReturnCode. Zero on success, else platform specified error.
+ inline ReturnCode delay(uint64_t i_nanoSeconds, uint64_t i_simCycles)
+ {
+ return FAPI2_RC_SUCCESS;
+ }
+}
#endif // FAPI2_UTILS_H_
OpenPOWER on IntegriCloud