dsp.cc
来自「M5,一个功能强大的多处理器系统模拟器.很多针对处理器架构,性能的研究都使用它作」· CC 代码 · 共 1,233 行 · 第 1/3 页
CC
1,233 行
int cc = 0; switch( op ) { case CMP_EQ: cc = ( a_values[i] == b_values[i] ); break; case CMP_LT: cc = ( a_values[i] < b_values[i] ); break; case CMP_LE: cc = ( a_values[i] <= b_values[i] ); break; } ccond |= cc << ( DSP_CTL_POS[DSP_CCOND] + i ); } writeDSPControl( dspctl, ccond, 1<<DSP_CCOND );}int32_tMipsISA::dspCmpg( int32_t a, int32_t b, int32_t fmt, int32_t sign, int32_t op ){ int i = 0; int nvals = SIMD_NVALS[fmt]; int32_t result = 0; uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; simdUnpack( a, a_values, fmt, sign ); simdUnpack( b, b_values, fmt, sign ); for( i=0; i<nvals; i++ ) { int cc = 0; switch( op ) { case CMP_EQ: cc = ( a_values[i] == b_values[i] ); break; case CMP_LT: cc = ( a_values[i] < b_values[i] ); break; case CMP_LE: cc = ( a_values[i] <= b_values[i] ); break; } result |= cc << i; } return( result );}int32_tMipsISA::dspCmpgd( int32_t a, int32_t b, int32_t fmt, int32_t sign, int32_t op, uint32_t *dspctl ){ int i = 0;; int nvals = SIMD_NVALS[fmt]; int32_t result = 0; int ccond = 0; uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; simdUnpack( a, a_values, fmt, sign ); simdUnpack( b, b_values, fmt, sign ); for( i=0; i<nvals; i++ ) { int cc = 0;; switch( op ) { case CMP_EQ: cc = ( a_values[i] == b_values[i] ); break; case CMP_LT: cc = ( a_values[i] < b_values[i] ); break; case CMP_LE: cc = ( a_values[i] <= b_values[i] ); break; } result |= cc << i; ccond |= cc << ( DSP_CTL_POS[DSP_CCOND] + i ); } writeDSPControl( dspctl, ccond, 1<<DSP_CCOND ); return( result );}int32_tMipsISA::dspPrece( int32_t a, int32_t infmt, int32_t insign, int32_t outfmt, int32_t outsign, int32_t mode ){ int i = 0; int sa = 0; int ninvals = SIMD_NVALS[infmt]; int noutvals = SIMD_NVALS[outfmt]; int32_t result; uint64_t in_values[SIMD_MAX_VALS]; uint64_t out_values[SIMD_MAX_VALS]; if( insign == SIGNED && outsign == SIGNED ) sa = SIMD_NBITS[infmt]; else if( insign == UNSIGNED && outsign == SIGNED ) sa = SIMD_NBITS[infmt] - 1; else if( insign == UNSIGNED && outsign == UNSIGNED ) sa = 0; simdUnpack( a, in_values, infmt, insign ); for( i=0; i<noutvals; i++ ) { switch( mode ) { case MODE_L: out_values[i] = in_values[i+(ninvals>>1)] << sa; break; case MODE_R: out_values[i] = in_values[i] << sa; break; case MODE_LA: out_values[i] = in_values[(i<<1)+1] << sa; break; case MODE_RA: out_values[i] = in_values[i<<1] << sa; break; } } simdPack( out_values, &result, outfmt ); return( result );}int32_tMipsISA::dspPrecrqu( int32_t a, int32_t b, uint32_t *dspctl ){ int i = 0; uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; uint64_t r_values[SIMD_MAX_VALS]; uint32_t ouflag = 0; int32_t result = 0; simdUnpack( a, a_values, SIMD_FMT_PH, SIGNED ); simdUnpack( b, b_values, SIMD_FMT_PH, SIGNED ); for( i=0; i<2; i++ ) { r_values[i] = dspSaturate( (int64_t)b_values[i] >> SIMD_NBITS[SIMD_FMT_QB] - 1, SIMD_FMT_QB, UNSIGNED, &ouflag ); r_values[i+2] = dspSaturate( (int64_t)a_values[i] >> SIMD_NBITS[SIMD_FMT_QB] - 1, SIMD_FMT_QB, UNSIGNED, &ouflag ); } simdPack( r_values, &result, SIMD_FMT_QB ); if( ouflag ) *dspctl = insertBits( *dspctl, 22, 22, 1 ); return result;}int32_tMipsISA::dspPrecrq( int32_t a, int32_t b, int32_t fmt, uint32_t *dspctl ){ uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; uint64_t r_values[SIMD_MAX_VALS]; uint32_t ouflag = 0; int32_t result; simdUnpack( a, a_values, fmt, SIGNED ); simdUnpack( b, b_values, fmt, SIGNED ); r_values[1] = dspSaturate( (int64_t)addHalfLsb( a_values[0], 16 ) >> 16, fmt+1, SIGNED, &ouflag ); r_values[0] = dspSaturate( (int64_t)addHalfLsb( b_values[0], 16 ) >> 16, fmt+1, SIGNED, &ouflag ); simdPack( r_values, &result, fmt+1 ); if( ouflag ) *dspctl = insertBits( *dspctl, 22, 22, 1 ); return result;}int32_tMipsISA::dspPrecrSra( int32_t a, int32_t b, int32_t sa, int32_t fmt, int32_t round ){ int i = 0; int nvals = SIMD_NVALS[fmt]; uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; uint64_t c_values[SIMD_MAX_VALS]; int32_t result = 0; simdUnpack( a, a_values, fmt, SIGNED ); simdUnpack( b, b_values, fmt, SIGNED ); for( i=0; i<nvals; i++ ) { if( round ) { c_values[i] = addHalfLsb( b_values[i], sa ) >> sa; c_values[i+1] = addHalfLsb( a_values[i], sa ) >> sa; } else { c_values[i] = b_values[i] >> sa; c_values[i+1] = a_values[i] >> sa; } } simdPack( c_values, &result, fmt+1 ); return result;}int32_tMipsISA::dspPick( int32_t a, int32_t b, int32_t fmt, uint32_t *dspctl ){ int i = 0; int nvals = SIMD_NVALS[fmt]; int32_t result; uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; uint64_t c_values[SIMD_MAX_VALS]; simdUnpack( a, a_values, fmt, UNSIGNED ); simdUnpack( b, b_values, fmt, UNSIGNED ); for( i=0; i<nvals; i++ ) { int condbit = DSP_CTL_POS[DSP_CCOND] + i; if( bits( *dspctl, condbit, condbit ) == 1 ) c_values[i] = a_values[i]; else c_values[i] = b_values[i]; } simdPack( c_values, &result, fmt ); return( result );}int32_tMipsISA::dspPack( int32_t a, int32_t b, int32_t fmt ){ int32_t result; uint64_t a_values[SIMD_MAX_VALS]; uint64_t b_values[SIMD_MAX_VALS]; uint64_t c_values[SIMD_MAX_VALS]; simdUnpack( a, a_values, fmt, UNSIGNED ); simdUnpack( b, b_values, fmt, UNSIGNED ); c_values[0] = b_values[1]; c_values[1] = a_values[0]; simdPack( c_values, &result, fmt ); return( result );}int32_tMipsISA::dspExtr( int64_t dspac, int32_t fmt, int32_t sa, int32_t round, int32_t saturate, uint32_t *dspctl ){ int32_t result = 0; uint32_t ouflag = 0; int64_t temp = 0; sa = bits( sa, 4, 0 ); if( sa > 0 ) { if( round ) { temp = (int64_t)addHalfLsb( dspac, sa ); if( dspac > 0 && temp < 0 ) { ouflag = 1; if( saturate ) temp = FIXED_SMAX[SIMD_FMT_L]; } temp = temp >> sa; } else temp = dspac >> sa; } else temp = dspac; dspac = checkOverflow( dspac, fmt, SIGNED, &ouflag ); if( ouflag ) { *dspctl = insertBits( *dspctl, 23, 23, ouflag ); if( saturate ) result = (int32_t)dspSaturate( temp, fmt, SIGNED, &ouflag ); else result = (int32_t)temp; } else result = (int32_t)temp; return( result );}int32_tMipsISA::dspExtp( int64_t dspac, int32_t size, uint32_t *dspctl ){ int32_t pos = 0; int32_t result = 0; pos = bits( *dspctl, 5, 0 ); size = bits( size, 4, 0 ); if( pos - (size+1) >= -1 ) { result = bits( dspac, pos, pos-size ); *dspctl = insertBits( *dspctl, 14, 14, 0 ); } else { result = 0; *dspctl = insertBits( *dspctl, 14, 14, 1 ); } return( result );}int32_tMipsISA::dspExtpd( int64_t dspac, int32_t size, uint32_t *dspctl ){ int32_t pos = 0; int32_t result = 0; pos = bits( *dspctl, 5, 0 ); size = bits( size, 4, 0 ); if( pos - (size+1) >= -1 ) { result = bits( dspac, pos, pos-size ); *dspctl = insertBits( *dspctl, 14, 14, 0 ); if( pos - (size+1) >= 0 ) *dspctl = insertBits( *dspctl, 5, 0, pos - (size+1) ); else if( (pos - (size+1)) == -1 ) *dspctl = insertBits( *dspctl, 5, 0, 63 ); } else { result = 0; *dspctl = insertBits( *dspctl, 14, 14, 1 ); } return( result );}voidMipsISA::simdPack( uint64_t *values_ptr, int32_t *reg, int32_t fmt ){ int i = 0; int nvals = SIMD_NVALS[fmt]; int nbits = SIMD_NBITS[fmt]; *reg = 0; for( i=0; i<nvals; i++ ) *reg |= (int32_t)bits( values_ptr[i], nbits-1, 0 ) << nbits*i;}voidMipsISA::simdUnpack( int32_t reg, uint64_t *values_ptr, int32_t fmt, int32_t sign ){ int i = 0; int nvals = SIMD_NVALS[fmt]; int nbits = SIMD_NBITS[fmt]; switch( sign ) { case SIGNED: for( i=0; i<nvals; i++ ) { values_ptr[i] = (uint64_t)bits( reg, nbits*(i+1)-1, nbits*i ); values_ptr[i] = signExtend( values_ptr[i], fmt ); } break; case UNSIGNED: for( i=0; i<nvals; i++ ) { values_ptr[i] = (uint64_t)bits( reg, nbits*(i+1)-1, nbits*i ); } break; }}voidMipsISA::writeDSPControl( uint32_t *dspctl, uint32_t value, uint32_t mask ){ uint32_t fmask = 0; if( mask & 0x01 ) fmask |= DSP_CTL_MASK[DSP_POS]; if( mask & 0x02 ) fmask |= DSP_CTL_MASK[DSP_SCOUNT]; if( mask & 0x04 ) fmask |= DSP_CTL_MASK[DSP_C]; if( mask & 0x08 ) fmask |= DSP_CTL_MASK[DSP_OUFLAG]; if( mask & 0x10 ) fmask |= DSP_CTL_MASK[DSP_CCOND]; if( mask & 0x20 ) fmask |= DSP_CTL_MASK[DSP_EFI]; *dspctl &= ~fmask; value &= fmask; *dspctl |= value;}uint32_tMipsISA::readDSPControl( uint32_t *dspctl, uint32_t mask ){ uint32_t fmask = 0; if( mask & 0x01 ) fmask |= DSP_CTL_MASK[DSP_POS]; if( mask & 0x02 ) fmask |= DSP_CTL_MASK[DSP_SCOUNT]; if( mask & 0x04 ) fmask |= DSP_CTL_MASK[DSP_C]; if( mask & 0x08 ) fmask |= DSP_CTL_MASK[DSP_OUFLAG]; if( mask & 0x10 ) fmask |= DSP_CTL_MASK[DSP_CCOND]; if( mask & 0x20 ) fmask |= DSP_CTL_MASK[DSP_EFI]; return( *dspctl & fmask );}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?