//*************************************************************************** // This file is property of and copyright by the ALICE HLT Project * // ALICE Experiment at CERN, All rights reserved. * // * // Primary Authors: Sergey Gorbunov * // Ivan Kisel * // for The ALICE HLT Project. * // * // Developed by: Igor Kulakov * // Maksym Zyzak * // * // Permission to use, copy, modify and distribute this software and its * // documentation strictly for non-commercial purposes is hereby granted * // without fee, provided that the above copyright notice appears in all * // copies and that both the copyright notice and this permission notice * // appear in the supporting documentation. The authors make no claims * // about the suitability of this software for any purpose. It is * // provided "as is" without express or implied warranty. * // * //*************************************************************************** #include "AliHLTTPCCAHitArea.h" #include "AliHLTTPCCASliceData.h" #include "AliHLTTPCCAGrid.h" #include "AliHLTTPCCARow.h" #include "debug.h" #ifndef NVALGRIND #include #endif // AliHLTTPCCAHitArea::AliHLTTPCCAHitArea( const AliHLTTPCCARow &row, const AliHLTTPCCASliceData &slice, // const sfloat_v &y, const sfloat_v &z, float dy, float dz, short_m mask ) // : fRow( row ), fSlice( slice ), // fHitYlst( Vc::Zero ), // fIh( Vc::Zero ), // fNy( fRow.Grid().Ny() ) // { // const AliHLTTPCCAGrid &grid = fRow.Grid(); // const sfloat_v minZ = z - dz; // const sfloat_v maxZ = z + dz; // const sfloat_v minY = y - dy; // const sfloat_v maxY = y + dy; // //std::cout << minZ[0] << " " << maxZ[0] << " " << minY[0] << " " << maxY[0] << " " << std::endl; // ushort_v bYmin, bZmin, bYmax; // boundary bin indexes // grid.GetBinBounded( minY, minZ, &bYmin, &bZmin ); // grid.GetBinBounded( maxY, maxZ, &bYmax, &fBZmax ); // fBDY = ( bYmax - bYmin + 1 ); // bin index span in y direction // fIndYmin = ( bZmin * fNy + bYmin ); // same as grid.GetBin(fMinY, fMinZ), i.e. the smallest bin index of interest // // fIndYmin + fBDY then is the largest bin index of interest with the same Z // fIz = bZmin; // const short_m invalidMask = !mask; // if ( !invalidMask.isEmpty() ) { // debugS() << "not all parts of the HitArea are valid: " << mask << std::endl; // fBZmax.makeZero( invalidMask ); // fBDY.makeZero( invalidMask ); // fIndYmin.makeZero( invalidMask ); // fIz.makeZero( invalidMask ); // // for given fIz (which is min atm.) get // fIh.gather( fSlice.FirstHitInBin( fRow ), fIndYmin, mask ); // first and // fHitYlst.gather( fSlice.FirstHitInBin( fRow ), fIndYmin + fBDY, mask ); // last hit index in the bin // } else { // fIh = fSlice.FirstHitInBin( fRow, fIndYmin ); // fHitYlst = fSlice.FirstHitInBin( fRow, fIndYmin + fBDY ); // } // assert( fHitYlst <= fRow.NHits() || invalidMask ); // debugS() << "HitArea created:\n" // << "bYmin: " << bYmin << "\n" // << "bZmin: " << bZmin << "\n" // << "bYmax: " << bYmax << "\n" // << "fBZmax: " << fBZmax << "\n" // << "fBDY: " << fBDY << "\n" // << "fIndYmin: " << fIndYmin << "\n" // << "fIz: " << fIz << "\n" // << "fHitYlst: " << fHitYlst << "\n" // << "fIh: " << fIh << "\n" // << "fNy: " << fNy << std::endl; // } // ushort_m AliHLTTPCCAHitArea::GetNext( NeighbourData *data ) // { // // get next hit index // VALGRIND_CHECK_VALUE_IS_DEFINED( fIh ); // VALGRIND_CHECK_VALUE_IS_DEFINED( fHitYlst ); // VALGRIND_CHECK_VALUE_IS_DEFINED( fIz ); // VALGRIND_CHECK_VALUE_IS_DEFINED( fBZmax ); // ushort_m yIndexOutOfRange = fIh >= fHitYlst; // current y is not in the area // ushort_m nextZIndexOutOfRange = fIz >= fBZmax; // there isn't any new z-line // VALGRIND_CHECK_VALUE_IS_DEFINED( yIndexOutOfRange ); // VALGRIND_CHECK_VALUE_IS_DEFINED( nextZIndexOutOfRange ); // if ( yIndexOutOfRange && nextZIndexOutOfRange ) { // all iterators are over the end // return ushort_m(false); // } // ushort_m isUsed = static_cast( short_v(fSlice.HitDataIsUsed( fRow ), fIh) != short_v( Vc::Zero ) ); // // at least one entry in the vector has (fIh >= fHitYlst && fIz < fBZmax) // ushort_m needNextZ = yIndexOutOfRange && !nextZIndexOutOfRange; // ushort_m needNextHit = (isUsed || yIndexOutOfRange) && !nextZIndexOutOfRange; // debugS() << "fIh >= fHitYlst: " << yIndexOutOfRange << " fIz >= fBZmax: " << nextZIndexOutOfRange << " -> " << needNextZ << std::endl; // // skip as long as fIh is outside of the interesting bin y-index // while ( !needNextHit.isEmpty() ) { // ++fIh( needNextHit ); // // if ( !needNextZ.isEmpty() ) { // slower // ++fIz( needNextZ ); // get new z-line // nextZIndexOutOfRange = fIz >= fBZmax; // // get next hit // fIndYmin( needNextZ ) += fNy; // fIh.gather( fSlice.FirstHitInBin( fRow ), fIndYmin, needNextZ ); // get first hit in cell, if z-line is new // fHitYlst.gather( fSlice.FirstHitInBin( fRow ), fIndYmin + fBDY, needNextZ ); // // } // isUsed = static_cast( short_v(fSlice.HitDataIsUsed( fRow ), fIh) != short_v( Vc::Zero ) ); // assert( fHitYlst <= fRow.NHits() || !needNextZ ); // yIndexOutOfRange = fIh >= fHitYlst; // needNextZ = yIndexOutOfRange && !nextZIndexOutOfRange; // // needNextHit = (isUsed && !yIndexOutOfRange) || (!isUsed && needNextZ); // slower // needNextHit = (isUsed || yIndexOutOfRange) && !nextZIndexOutOfRange; // incorrect // debugS() << "fIh >= fHitYlst: " << yIndexOutOfRange << " fIz >= fBZmax: " << nextZIndexOutOfRange << " -> " << needNextZ << std::endl; // } // data->fValid = !yIndexOutOfRange && !isUsed; // const sfloat_m valid( data->fValid ); // data->fY.makeZero(); // data->fY.gather( fSlice.HitDataY( fRow ), fIh, valid ); // data->fZ.makeZero(); // data->fZ.gather( fSlice.HitDataZ( fRow ), fIh, valid ); // data->fLinks = fIh.staticCast(); // ++fIh; // debugS() << "HitArea found next. New state:\n" // << "fIndYmin: " << fIndYmin << "\n" // << "fIz: " << fIz << "\n" // << "fHitYlst: " << fHitYlst << "\n" // << "fIh: " << fIh << std::endl; // return data->fValid; // } // area which doesn't use the Grid AliHLTTPCCAHitArea::AliHLTTPCCAHitArea( const AliHLTTPCCARow &row, const AliHLTTPCCASliceData &slice, const sfloat_v &y, const sfloat_v &z, float dy, float dz, short_m mask ) : fRow(row), fSlice(slice) { fMinY = y - dy; fMaxY = y + dy; fMinZ = z - dz; fMaxZ = z + dz; //std::cout << value(fMinZ[0]) << " " << value(fMaxZ[0]) << " " << value(fMinY[0]) << " " << value(fMaxY[0]) << " " << std::endl; fCurHitI = -1; fCurHitData.fValid = short_m(true); fCurHitData.fY = -10000; fCurHitData.fZ = -10000; fCurHitData.fLinks = -1; } // AliHLTTPCCAHitArea_ArBB::AliHLTTPCCAHitArea_ArBB short_m AliHLTTPCCAHitArea::GetNext( AliHLTTPCCAHitArea::NeighbourData *data ) { const short NRowHits = fRow.NHits(); // go to the next hit fCurHitI++; fCurHitData.fValid &= (fCurHitI < NRowHits); // check whether the hit is not used // dense isUsed = fill(false, taskSize); short_m isUsed(true); isUsed = ( short_v( fSlice.HitDataIsUsed( fRow ), static_cast(fCurHitI), fCurHitData.fValid ) != short_v(Vc::Zero) ); fCurHitData.fValid = fCurHitData.fValid && !isUsed; // check whether hit is in the needed region fCurHitData.fY.gather( fSlice.HitDataY( fRow ), static_cast(fCurHitI), fCurHitData.fValid ); fCurHitData.fZ.gather( fSlice.HitDataZ( fRow ), static_cast(fCurHitI), fCurHitData.fValid ); fCurHitData.fValid &= static_cast(IsInRange( fCurHitData.fY, fCurHitData.fZ )); // if the hit is not appropriate let's find an appropriate hits sfloat_m needNextHitMask = !fCurHitData.fValid && (fCurHitI < NRowHits); while ( ! needNextHitMask.isEmpty() ) { // try next hit fCurHitI(static_cast(needNextHitMask))++; needNextHitMask = needNextHitMask && (fCurHitI < NRowHits); // check whether the hit is not used isUsed = ( short_v( fSlice.HitDataIsUsed( fRow ), static_cast(fCurHitI), static_cast(needNextHitMask) ) != short_v(Vc::Zero) ); // check whether hit is in the needed region fCurHitData.fY.gather( fSlice.HitDataY( fRow ), static_cast(fCurHitI), needNextHitMask && static_cast(!isUsed)); fCurHitData.fZ.gather( fSlice.HitDataZ( fRow ), static_cast(fCurHitI), needNextHitMask && static_cast(!isUsed)); fCurHitData.fValid = ( static_cast(!needNextHitMask) && fCurHitData.fValid ) || ( static_cast(needNextHitMask && IsInRange( fCurHitData.fY, fCurHitData.fZ )) && !isUsed && (fCurHitI < NRowHits)); // fCurHitData.valid = IsInRange( fCurHitData.y, fCurHitData.z ); needNextHitMask = needNextHitMask && !fCurHitData.fValid; }; fCurHitData.fLinks = fCurHitI; *data = fCurHitData; return fCurHitData.fValid; } // -- ArBB TODO find right place #include #include "AliHLTTPCCADef.h" using arbb::dense; using arbb::f32; using arbb::i16; //using arbb::boolean; // AliHLTTPCCAHitArea_ArBB::AliHLTTPCCAHitArea_ArBB() // { // } AliHLTTPCCAHitArea_ArBB::AliHLTTPCCAHitArea_ArBB( const AliHLTTPCCARowHit::TDense<1>& row, const dense &y, const dense &z, f32 dy, f32 dz, const dense& mask ) : fRow(row) { fMinY = y - dy; fMaxY = y + dy; fMinZ = z - dz; fMaxZ = z + dz; //std::cout << value(fMinZ[0]) << " " << value(fMaxZ[0]) << " " << value(fMinY[0]) << " " << value(fMaxY[0]) << " " << std::endl; const THitI_ArBB taskSize = y.length(); fCurHitI = fill(-1, taskSize); NeighbourData zero(-10000,-10000,-1,true); fCurHitData = fill(zero, taskSize); fCurHitData.SetValid( mask ); } // AliHLTTPCCAHitArea_ArBB::AliHLTTPCCAHitArea_ArBB AliHLTTPCCAHitArea_ArBB::NeighbourData::TDense<1> AliHLTTPCCAHitArea_ArBB::GetNext() // TODO more clever implementation! { const THitI_ArBB NRowHits = static_cast(fRow.length()); const THitI_ArBB taskSize = fCurHitI.length(); // go to the next hit fCurHitI++; fCurHitData.SetValid( fCurHitData.Valid() && (fCurHitI < NRowHits) ); // check whether the hit is not used dense isUsed = fill(true, taskSize); isUsed = gather( fRow.IsUsed(), fCurHitI, static_cast(-10000), fill(-10000, taskSize), fCurHitData.Valid() ) != 0; // at the begining fCurHitData.valid contains "false" only for outOfBound indices fCurHitData.SetValid( fCurHitData.Valid() && !isUsed ); // check whether hit is in the needed region fCurHitData.SetY( gather( fRow.Y(), fCurHitI, static_cast(-10000), fCurHitData.Y(), fCurHitData.Valid() ) ); fCurHitData.SetZ( gather( fRow.Z(), fCurHitI, static_cast(-10000), fCurHitData.Z(), fCurHitData.Valid() ) ); fCurHitData.SetValid( fCurHitData.Valid() && IsInRange( fCurHitData ) ); // if the hit is not appropriate let's find an appropriate hits dense needNextHitMask = !fCurHitData.Valid() && (fCurHitI < NRowHits); _for (, any( needNextHitMask ), ) { // try next hit fCurHitI = select(needNextHitMask, fCurHitI+1, fCurHitI); needNextHitMask = needNextHitMask && (fCurHitI < NRowHits); // check whether the hit is not used isUsed = gather( fRow.IsUsed(), fCurHitI, static_cast(-10000), fill(-10000, taskSize), needNextHitMask ) != 0; // check whether hit is in the needed region fCurHitData.SetY( gather( fRow.Y(), fCurHitI, static_cast(-10000), fCurHitData.Y(), needNextHitMask && !isUsed ) ); fCurHitData.SetZ( gather( fRow.Z(), fCurHitI, static_cast(-10000), fCurHitData.Z(), needNextHitMask && !isUsed ) ); fCurHitData.SetValid( ( !needNextHitMask && fCurHitData.Valid() ) || ( needNextHitMask && IsInRange( fCurHitData ) && !isUsed && (fCurHitI < NRowHits) ) ); needNextHitMask = !fCurHitData.Valid() && (fCurHitI < NRowHits); } _end_for; fCurHitData.SetLinks( fCurHitI ); return fCurHitData; }