クラス メソッド、演算子、データ メンバー - 2023.2 日本語

Vitis 高位合成ユーザー ガイド (UG1399)

Document ID
UG1399
Release Date
2023-12-18
Version
2023.2 日本語

通常、ネイティブの C/C++ 整数型で実行可能な有効な演算は、ap_[u]fixed 型で演算子のオーバーロードを使用するとサポートされます。オーバーロードされた演算子に加え、ビット レベルの演算を実行しやすくする演算子およびメソッドが含まれています。

2 進数の算術演算子

加算

ap_[u]fixed::RType ap_[u]fixed::operator + (ap_[u]fixed op)

任意精度の固定小数点と指定したオペランド op を加算します。

オペランドには、次のいずれかの整数型を使用できます。

  • ap_[u]fixed
  • ap_[u]int
  • C/C++

結果のデータ型 ap_[u]fixed::RType は、2 つのオペランドのデータ型によります。

ap_fixed<76, 63> Result;

ap_fixed<5, 2> Val1 = 1.125;
ap_fixed<75, 62> Val2 = 6721.35595703125;

Result = Val1 + Val2; //Yields 6722.480957

Val2 の方が整数部および小数部のビット幅が広いため、結果値をすべて格納できるようにするため、結果のデータ型の幅はこのビット幅に 1 を足したものになります。

データの幅を指定すると、次に示すように、べき関数を使用してリソースが制御されます。同様に、AMDでは、固定小数点演算の幅を指定する代わりに、格納された結果の幅を指定することをお勧めします。

ap_ufixed<16,6> x=5; 
ap_ufixed<16,7>y=hl::rsqrt<16,6>(x+x); 

減算

ap_[u]fixed::RType ap_[u]fixed::operator - (ap_[u]fixed op)

任意精度の固定小数点値から指定したオペランド op を減算します。

結果のデータ型 ap_[u]fixed::RType は、2 つのオペランドのデータ型によります。

ap_fixed<76, 63> Result;

ap_fixed<5, 2> Val1 = 1625.153;
ap_fixed<75, 62> Val2 = 6721.355992351;

Result = Val2 - Val1; // Yields 6720.23057

Val2 の方が整数部および小数部のビット幅が広いため、結果値をすべて格納できるようにするため、結果のデータ型の幅はこのビット幅に 1 を足したものになります。

乗算

ap_[u]fixed::RType ap_[u]fixed::operator * (ap_[u]fixed op)

任意精度の固定小数点値を指定したオペランド op と乗算します。

ap_fixed<80, 64> Result;

ap_fixed<5, 2> Val1 = 1625.153;
ap_fixed<75, 62> Val2 = 6721.355992351;

Result = Val1 * Val2; // Yields 7561.525452

この例では、Val1Val2 を乗算しています。この結果のデータ型は、整数部のビット幅と小数部のビット幅の和になります。

除算

ap_[u]fixed::RType ap_[u]fixed::operator / (ap_[u]fixed op)

任意精度の固定小数点値を指定したオペランド op で除算します。

ap_fixed<84, 66> Result;

ap_fixed<5, 2> Val1 = 1625.153;
ap_fixed<75, 62> Val2 = 6721.355992351;

Val2 / Val1; // Yields 5974.538628

この例では、Val2Val1 を除算しています。十分な精度を保持するため、次のようになります。

  • 結果のデータ型の整数ビット幅は、Val2 の整数ビット幅と、Val1 の小数ビット幅の和になります。
  • 結果のデータ型の小数ビット幅は、Val2 の小数ビット幅と等しくなります。

ビット単位の論理演算子

ビット単位 OR

ap_[u]fixed::RType ap_[u]fixed::operator | (ap_[u]fixed op)

任意精度の固定小数点と任意のオペランド op にビット単位演算を適用します。

ap_fixed<75, 62> Result;

ap_fixed<5, 2> Val1 = 1625.153;
ap_fixed<75, 62> Val2 = 6721.355992351;

Result = Val1 | Val2; // Yields 6271.480957

ビット単位 AND

ap_[u]fixed::RType ap_[u]fixed::operator & (ap_[u]fixed op)

任意精度の固定小数点と任意のオペランド op にビット単位演算を適用します。

ap_fixed<75, 62> Result;

ap_fixed<5, 2> Val1 = 1625.153;
ap_fixed<75, 62> Val2 = 6721.355992351;

Result = Val1 & Val2;  // Yields 1.00000

ビット単位 XOR

ap_[u]fixed::RType ap_[u]fixed::operator ^ (ap_[u]fixed op)

任意精度の固定小数点と任意のオペランド opxor ビット単位演算を適用します。

ap_fixed<75, 62> Result;

ap_fixed<5, 2> Val1 = 1625.153;
ap_fixed<75, 62> Val2 = 6721.355992351;

Result = Val1 ^ Val2; // Yields 6720.480957

インクリメントおよびデクリメント演算子

前置インクリメント

ap_[u]fixed ap_[u]fixed::operator ++ ()

任意精度の固定小数点変数を 1 インクリメントします。

ap_fixed<25, 8> Result;
ap_fixed<8, 5> Val1 = 5.125;

Result = ++Val1; // Yields 6.125000

後置インクリメント

ap_[u]fixed ap_[u]fixed::operator ++ (int)

この演算関数は、次を実行します。

  • 任意精度の固定小数点変数を 1 インクリメント。
  • この任意精度の固定小数点の元の値を返す。
    ap_fixed<25, 8> Result;
    ap_fixed<8, 5> Val1 = 5.125;
    
    Result = Val1++; // Yields 5.125000

前置デクリメント

ap_[u]fixed ap_[u]fixed::operator -- ()

任意精度の固定小数点変数を 1 デクリメントします。

ap_fixed<25, 8> Result;
ap_fixed<8, 5> Val1 = 5.125;

Result = --Val1; // Yields 4.125000

後置デクリメント

ap_[u]fixed ap_[u]fixed::operator -- (int)

この演算関数は、次を実行します。

  • 任意精度の固定小数点変数を 1 デクリメント。
  • この任意精度の固定小数点の元の値を返す。
    ap_fixed<25, 8> Result;
    ap_fixed<8, 5> Val1 = 5.125;
    
    Result = Val1--; // Yields 5.125000

単項演算子

加算

ap_[u]fixed ap_[u]fixed::operator + ()

任意精度の固定小数点変数のセルフ コピーを返します。

ap_fixed<25, 8> Result;
ap_fixed<8, 5> Val1 = 5.125;

Result = +Val1;  // Yields 5.125000

減算

ap_[u]fixed::RType ap_[u]fixed::operator - ()

任意精度の固定小数点変数の負の値を返します。

ap_fixed<25, 8> Result;
ap_fixed<8, 5> Val1 = 5.125;

Result = -Val1; // Yields -5.125000

0 との等価比較

bool ap_[u]fixed::operator ! ()

この演算関数は、次を実行します。

  • 任意精度の固定小数点変数を 0 と比較。
  • 結果を返す。
    bool  Result;
    ap_fixed<8, 5> Val1 = 5.125;
    
    Result = !Val1; // Yields false

ビット単位の反転

ap_[u]fixed::RType ap_[u]fixed::operator ~ ()

任意精度の固定小数点変数のビット単位の補数を返します。

ap_fixed<25, 15> Result;
ap_fixed<8, 5> Val1 = 5.125;

Result = ~Val1; // Yields -5.25

シフト演算子

符号なし左シフト

ap_[u]fixed ap_[u]fixed::operator << (ap_uint<_W2> op) 

この演算関数は、次を実行します。

  • 指定した整数オペランド分左にシフト。
  • 結果を返す。

オペランドには次の C/C++ の整数型を使用できます。

  • char
  • short
  • int
  • long

左シフト演算で返されるデータ型は、シフトされたデータ型と同じ幅になります。

注記: シフトではオーバーフローまたは量子化モードはサポートされていません。
ap_fixed<25, 15> Result;
ap_fixed<8, 5> Val = 5.375;

ap_uint<4> sh = 2;

Result = Val << sh; // Yields -10.5

結果のビット幅は (W = 25I = 15) です。左シフト演算の結果のデータ型は Val と同じであるため、次のようになります。

  • Val の上位 2 ビットがシフト アウトされます。
  • 結果は -10.5 になります。

結果が 21.5 になるようにするには、ap_ufixed<10, 7>(Val) のように、まず Valap_fixed<10, 7> にキャストする必要があります。

符号付き左シフト

ap_[u]fixed ap_[u]fixed::operator << (ap_int<_W2> op)

この演算子は、次を実行します。

  • 指定した整数オペランド分左にシフト。
  • 結果を返す。

オペランドが正か負かによって、シフトの方向が変わります。

  • オペランドが正の場合は右シフトが実行されます。
  • オペランドが負の場合は左シフト (逆方向) が実行されます。

オペランドには次の C/C++ の整数型を使用できます。

  • char
  • short
  • int
  • long

右シフト演算で返されるデータ型は、シフトされたデータ型と同じ幅になります。

ap_fixed<25, 15,  false> Result;
ap_uint<8, 5> Val = 5.375;

ap_int<4> Sh = 2;
Result = Val << sh; // Shift left, yields -10.25

Sh = -2;
Result = Val << sh; // Shift right, yields 1.25

符号なし右シフト

ap_[u]fixed ap_[u]fixed::operator >> (ap_uint<_W2> op) 

この演算関数は、次を実行します。

  • 指定した整数オペランド分右にシフト。
  • 結果を返す。

オペランドには次の C/C++ の整数型を使用できます。

  • char
  • short
  • int
  • long

右シフト演算で返されるデータ型は、シフトされたデータ型と同じ幅になります。

ap_fixed<25, 15> Result;
ap_fixed<8, 5> Val = 5.375;

ap_uint<4> sh = 2;

Result = Val >> sh; // Yields 1.25

すべての上位ビットを保持する必要がある場合は、ap_fixed<10, 5>(Val) のように、まず Val の小数部のビット幅を拡張します。

符号付き右シフト

ap_[u]fixed ap_[u]fixed::operator >> (ap_int<_W2> op) 

この演算子は、次を実行します。

  • 指定した整数オペランド分右にシフト。
  • 結果を返す。

オペランドが正か負かによって、シフトの方向が変わります。

  • オペランドが正の場合は右シフトが実行されます。
  • オペランドが負の場合は左シフト (逆方向) が実行されます。

オペランドには C/C++ の整数型 (charshortint、または long) を使用できます。

右シフト演算で返されるデータ型は、シフトされるデータ型と同じ幅になります。次に例を示します。

ap_fixed<25, 15,  false> Result;
ap_uint<8, 5> Val = 5.375;

ap_int<4> Sh = 2;
Result = Val >> sh; // Shift right, yields 1.25

Sh = -2;
Result = Val >> sh; // Shift left,  yields -10.5

1.25

比較演算子

等価比較

bool ap_[u]fixed::operator == (ap_[u]fixed op)

任意精度の固定小数点変数と指定したオペランドを比較します。

等しい場合は true、等しくない場合は false を返します。

オペランド op のデータ型には、ap_[u]fixedap_int または C/C++ の整数型を使用できます。次に例を示します。

bool Result;

ap_ufixed<8, 5> Val1 = 1.25;
ap_fixed<9, 4> Val2 = 17.25;
ap_fixed<10, 5> Val3 = 3.25;

Result = Val1 == Val2; // Yields  true
Result = Val1 == Val3; // Yields  false

不等価比較

bool ap_[u]fixed::operator != (ap_[u]fixed op)

任意精度の固定小数点変数を指定したオペランドと比較します。

等しくない場合は true、等しい場合は false を返します。

オペランド op のデータ型には、次を使用できます。

  • ap_[u]fixed
  • ap_int
  • C または C++ の整数型

次に例を示します。

bool Result;

ap_ufixed<8, 5> Val1 = 1.25;
ap_fixed<9, 4> Val2 = 17.25;
ap_fixed<10, 5> Val3 = 3.25;

Result = Val1 != Val2; // Yields false
Result = Val1 != Val3; // Yields true

以上

bool ap_[u]fixed::operator >= (ap_[u]fixed op)

変数を指定のオペランドと比較します。

変数がオペランド以上の場合は true、そうでない場合は false を返します。

オペランド op のデータ型には、ap_[u]fixedap_int または C/C++ の整数型を使用できます。

次に例を示します。

bool Result;

ap_ufixed<8, 5> Val1 = 1.25;
ap_fixed<9, 4> Val2 = 17.25;
ap_fixed<10, 5> Val3 = 3.25;

Result = Val1 >= Val2; // Yields true
Result = Val1 >= Val3; // Yields false

以下

bool ap_[u]fixed::operator <= (ap_[u]fixed op)

変数と指定のオペランドを比較し、変数がオペランド以下の場合は true、そうでない場合は false を返します。

オペランド op のデータ型には、ap_[u]fixedap_int または C/C++ の整数型を使用できます。

次に例を示します。

bool Result;

ap_ufixed<8, 5> Val1 = 1.25;
ap_fixed<9, 4> Val2 = 17.25;
ap_fixed<10, 5> Val3 = 3.25;

Result = Val1 <= Val2; // Yields true
Result = Val1 <= Val3; // Yields true

大なり (>)

bool ap_[u]fixed::operator > (ap_[u]fixed op)

変数を指定のオペランドと比較し、変数がオペランドより大きい場合は true、そうでない場合は false を返します。

オペランド op のデータ型には、ap_[u]fixedap_int または C/C++ の整数型を使用できます。

次に例を示します。

bool Result;

ap_ufixed<8, 5> Val1 = 1.25;
ap_fixed<9, 4> Val2 = 17.25;
ap_fixed<10, 5> Val3 = 3.25;

Result = Val1 > Val2; // Yields false
Result = Val1 > Val3; // Yields false

小なり (<)

bool ap_[u]fixed::operator < (ap_[u]fixed op)

変数と指定のオペランドを比較し、変数がオペランド未満の場合は true、そうでない場合は false を返します。

オペランド op のデータ型には、ap_[u]fixedap_int または C/C++ の整数型を使用できます。次に例を示します。

bool Result;

ap_ufixed<8, 5> Val1 = 1.25;
ap_fixed<9, 4> Val2 = 17.25;
ap_fixed<10, 5> Val3 = 3.25;

Result = Val1 < Val2; // Yields false
Result = Val1 < Val3; // Yields true

ビット演算子

ビットの選択と設定

af_bit_ref ap_[u]fixed::operator [] (int bit) 

任意精度の固定小数点値から 1 ビット選択し、それを返します。

戻り値は、ap_[u]fixed 変数の対応するビットをセットまたはクリアできる参照値です。ビット引数は整数値である必要があり、選択するビットの指数を指定します。最下位ビットの指数は 0 です。最大指数はこの ap_[u]fixed 変数のビット幅から 1 を引いた値になります。

結果のデータ型は af_bit_ref で、値は 0 または 1 です。次に例を示します。

ap_int<8, 5> Value = 1.375;

Value[3]; // Yields  1
Value[4]; // Yields  0

Value[2] = 1; // Yields 1.875
Value[3] = 0; // Yields 0.875

ビット範囲

af_range_ref af_(u)fixed::range (unsigned Hi, unsigned Lo)
af_range_ref af_(u)fixed::operator [] (unsigned Hi, unsigned Lo) 

この演算は、ビット セレクト演算子 [] に似ていますが、1 ビットではなくビットの範囲を指定し、

任意精度の固定小数点変数からビットのグループを選択します。引数 Hi は範囲の上限のビットを指定し、引数 Lo は下限のビットを指定します。LoHi よりも大きい場合は、選択されたビットが逆順で返されます。

戻り値のデータ型 af_range_ref は、Hi および Lo で指定される ap_[u]fixed 変数の範囲の参照です。次に例を示します。

ap_uint<4> Result = 0;
ap_ufixed<4, 2> Value = 1.25;
ap_uint<8> Repl = 0xAA;

Result = Value.range(3, 0); // Yields: 0x5
Value(3, 0) = Repl(3, 0); // Yields: -1.5

// when Lo > Hi, return the reverse bits string
Result = Value.range(0, 3); // Yields: 0xA

範囲選択

af_range_ref af_(u)fixed::range ()
af_range_ref af_(u)fixed::operator []

これは、範囲選択演算子 [] の特殊ケースで、任意精度の固定小数点値からすべてのビットを標準の順序で選択します。

戻り値のデータ型 af_range_ref は、Hi = W - 1 および Lo = 0 で指定される範囲の参照です。次に例を示します。

ap_uint<4> Result = 0;

ap_ufixed<4, 2> Value = 1.25;
ap_uint<8> Repl = 0xAA;

Result = Value.range(); // Yields: 0x5
Value() = Repl(3, 0); // Yields: -1.5

長さ

int ap_[u]fixed::length ()

ビット数を表す整数値を任意精度の整数値で返します。データ型または値に使用できます。次に例を示します。

ap_ufixed<128, 64> My128APFixed;

int bitwidth = My128APFixed.length(); // Yields 128

明示的な変換メソッド

固定小数点から double 型

double ap_[u]fixed::to_double ()

このメンバー関数は、固定小数点値を IEEE の倍精度フォーマットに変換します。次に例を示します。

ap_ufixed<256, 77> MyAPFixed = 333.789;
double Result;

Result = MyAPFixed.to_double(); // Yields 333.789

固定小数点から浮動小数点

float ap_[u]fixed::to_float()

このメンバー関数は、固定小数点値を IEEE の浮動精度フォーマットに変換します。次に例を示します。

ap_ufixed<256, 77> MyAPFixed = 333.789;
float Result;

Result = MyAPFixed.to_float();  // Yields 333.789

固定小数点から半精度浮動小数点

half ap_[u]fixed::to_half()

このメンバー関数は、固定小数点値を HLS の半精度 (16 ビット) 浮動精度フォーマットに変換します。次に例を示します。

ap_ufixed<256, 77> MyAPFixed = 333.789;
half Result;

Result = MyAPFixed.to_half();  // Yields 333.789

固定小数点から ap_int 型

ap_int ap_[u]fixed::to_ap_int ()

このメンバー関数は、この固定小数点値を、小数ビットを切り捨てた整数ビットのみを含む ap_int 型に変換します。次に例を示します。

ap_ufixed<256, 77> MyAPFixed = 333.789;
ap_uint<77> Result;

Result = MyAPFixed.to_ap_int(); //Yields 333

固定小数点から整数型

int ap_[u]fixed::to_int ()
unsigned ap_[u]fixed::to_uint ()
ap_slong ap_[u]fixed::to_int64 ()
ap_ulong ap_[u]fixed::to_uint64 ()

このメンバー関数は、固定小数点値を C のビルトイン整数型に変換します。次に例を示します。

ap_ufixed<256, 77> MyAPFixed = 333.789;
unsigned int  Result;

Result = MyAPFixed.to_uint(); //Yields 333

unsigned long long Result;
Result = MyAPFixed.to_uint64(); //Yields 333

コンパイル時のデータ型属性へのアクセス

ap_[u]fixed<> 型には、データ型のサイズと設定がコンパイル時に決定されるようにする複数のスタティック メンバーがあります。このデータ型には、static const メンバーである widthiwidthqmode、および omode があります。

static const int width = _AP_W;
static const int iwidth = _AP_I;
static const ap_q_mode qmode = _AP_Q;
static const ap_o_mode omode = _AP_O;

これらのデータ メンバーは、既存の ap_[u]fixed<> 型から次の情報を抽出するために使用できます。

width
データ型の幅。
iwidth
データ型の整数部分の幅。
qmode
データ型の量子化モード。
omode
データ型のオーバーフロー モード。

これらのデータ メンバーを使用すると、たとえば既存の ap_[u]fixed<> 型のデータ幅を抽出して、コンパイル時に別の ap_[u]fixed<> 型を作成できます。

次の例は、変数 Res のサイズを、変数 Val1 および Val2 よりも 1 ビット大きくし、同じ量子化モードで定義します。

// Definition of basic data type
#define INPUT_DATA_WIDTH 12
#define IN_INTG_WIDTH 6
#define IN_QMODE AP_RND_ZERO
#define IN_OMODE AP_WRAP
typedef ap_fixed<INPUT_DATA_WIDTH, IN_INTG_WIDTH, IN_QMODE, IN_OMODE> data_t;
// Definition of variables 
data_t Val1, Val2;
// Res is automatically sized at run-time to be 1-bit greater than INPUT_DATA_WIDTH 
// The bit growth in Res will be in the integer bits
ap_int<data_t::width+1, data_t::iwidth+1, data_t::qmode, data_t::omode> Res = Val1 + 
Val2;

これにより、INPUT_DATA_WIDTH、IN_INTG_WIDTH、または data_t の量子化モードの値をアップデートした場合でも、Vitis HLS で加算によるビット増加が正しくモデリングされるようになります。