ZHCUAU3J January 2018 – March 2024
编译器库中提供了一组实用程序,用于为 C7000 编写独立于矢量宽度的代码。要使用这些实用程序,请在源代码中 #include c7x_scalable.h
。
这些实用程序仅可在 C++ 代码中使用,因为它们的实现中使用了 C++ 语言功能。
使用 TI C7000 编译器或使用 TI C7000 主机仿真进行编译时,可使用这些实用程序。
以下 API 可用,c7x_scalable.h
文件中对所有这些 API 进行了更详细的描述:
c7x::max_simd<T>::value
c7x::element_count_of<T>::value
c7x::element_type_of<T>::type
c7x::component_type_of<T>::type
c7x::make_vector<T,N>::type
c7x::make_full_vector<T>::type
c7x::is_target_vector<T>::value
c7x::char_vec
c7x::short_vec
etc
c7x::char_hvec
c7x::short_hvec
etc
c7x::char_qvec
c7x::short_qvec
etc
c7x::char_vec_ptr
c7x::const_short_vec_ptr
etc
c7x::reinterpret<T>(v)
c7x::convert<T>(v)
c7x::as_char_vec(v)
c7x::convert_short_vec(v)etc
c7x::se_veclen<T>::value
c7x::se_eletype<T>::value
c7x::sa_veclen<T>::value
c7x::strm_eng<I,T>::get()
c7x::strm_eng<I,T>::get_adv()
c7x::strm_agen<I,T>::get(p)
c7x::strm_agen<I,T>::get_adv(p)
c7x::strm_agen<I,T>::get_vpred()
以下宏由 c7x_mma.h
定义,可用于确定有关 MMA 与可扩展矢量编程模型配合使用的信息:
宏语法 | 说明 |
---|---|
__MMA_A_MAT_BYTES__ | A 矩阵的大小(以字节为单位)。目前,每个 A 矩阵包含一行。 |
__MMA_A_ROW_WIDTH_BYTES__ | A 矩阵中一行的大小(以字节为单位)。 |
__MMA_A_ROWS__ | A 矩阵中的行数。 |
__MMA_A_COLS(ebytes) | 给定 A 矩阵各元素中字节数时该矩阵中的列数。通常对 sizeof() 有用。例如,__MMA_A_COLS(sizeof(short)) 。 |
__MMA_A_ENTRIES__ | 可以包含在 A 存储中的 A 条目数。 |
__MMA_B_MAT_BYTES__ | B 矩阵的大小(以字节为单位)。 |
__MMA_B_ROW_WIDTH_BYTES__ | B 矩阵中一行的大小(以字节为单位)。 |
__MMA_B_ROWS(ebytes) | 给定 B 矩阵各元素中的字节数时该矩阵中的行数。通常对 sizeof() 有用。例如,__MMA_B_ROWS(sizeof(short)) 。 |
__MMA_B_COLS(ebytes) | 给定 B 矩阵各元素中的字节数时该矩阵中的列数。通常对 sizeof() 有用。例如,__MMA_B_COLS(sizeof(short)) 。 |
__MMA_C_MAT_BYTES__ | C 矩阵的大小。目前,每个 C 矩阵包含一行。目前,对于较大的累加器,C 矩阵比 A 矩阵宽 4 倍。 |
__MMA_C_ROW_WIDTH_BYTES__ | C 矩阵中行的大小。 |
__MMA_C_ROWS__ | C 矩阵中的行数。 |
__MMA_C_COLS(ebytes) | 给定 C 矩阵各元素中的字节数时该矩阵中的列数。通常对 sizeof() 有用。例如,__MMA_C_COLS(sizeof(short)) 。 |
__MMA_C_ENTRIES__ | 可以包含在 C 存储中的 C 条目数。 |
作为一个中等复杂度的示例,以下是使用输入类型作为模板的 memcpy 的 C++ 函数模板的实现。此示例使用流引擎和流地址生成器(请参阅节 4.15)。
#include <c7x_scalable.h>
using namespace c7x;
/* memcpy_scalable_strm<typename S>(const S*in, S *out, int len)
*
* S - A basic data type such as short or float.
* in - The input buffer.
* out - The output buffer.
* len - The number of elements to copy.
*
* Defaulted template arguments:
* V - A full vector type of S
*/
template<typename S,
typename V = typename make_full_vector<S>::type>
void memcpy_scalable_strm(const S *restrict in, S *restrict out, int len)
{
/*
* Find the maximum number of vector loads/stores needed to copy the buffer,
* including any remainder.
*/
int cnt = len / element_count_of<V>::value;
cnt += (len % element_count_of<V>::value > 0);
/* Initialize the SE for a linear read in and the SA for a linear write out. */
__SE_TEMPLATE_v1 in_tmplt = __gen_SE_TEMPLATE_v1();
__SA_TEMPLATE_v1 out_tmplt = __gen_SA_TEMPLATE_v1();
in_tmplt.VECLEN = se_veclen<V>::value;
in_tmplt.ELETYPE = se_eletype<V>::value;
in_tmplt.ICNT0 = len;
out_tmplt.VECLEN = sa_veclen<V>::value;
out_tmplt.ICNT0 = len;
__SE0_OPEN(in, in_tmplt);
__SA0_OPEN(out_tmplt);
/* Perform the copy. If there is remainder, the last store will be predicated. */
int i;
for (i = 0; i < cnt; i++)
{
V tmp = strm_eng<0, V>::get_adv();
__vpred pred = strm_agen<0, V>::get_vpred();
V *addr = strm_agen<0, V>::get_adv(out);
__vstore_pred(pred, addr, tmp);
}
__SE0_CLOSE();
__SA0_CLOSE();
}