SHiP Geometry
SHiP experiment geometry implementation using GeoModel.
Loading...
Searching...
No Matches
Namespaces | Classes | Functions | Variables
SHiPGeometry::SBT Namespace Reference

Compile-time parameters of the Surround Background Tagger (SBT). More...

Namespaces

namespace  detail
 

Classes

struct  HeliumPiece
 The innermost free region of the SBT, and the helium that fills it. More...
 
struct  HeliumSlabs
 
struct  SBTParams
 Every dimension the SBT geometry is parameterised by (mm). More...
 

Functions

constexpr double subLength (const SBTParams &params=kSBT)
 Length of one sub-frustum along Z (mm).
 
constexpr double webHeight (const SBTParams &params=kSBT)
 Clear web height = height - 2*flange thickness (mm).
 
constexpr int nWalls (const SBTParams &params=kSBT)
 Number of aluminium walls per container (nCells + 1).
 
constexpr double zExit (const SBTParams &params=kSBT)
 Exit-face Z in the DecayVolume local frame (mm).
 
constexpr double xGrowth (const SBTParams &params=kSBT)
 dx_half/dz of the frustum (dimensionless).
 
constexpr double yGrowth (const SBTParams &params=kSBT)
 dy_half/dz of the frustum (dimensionless).
 
constexpr double xHalfAt (double z_mm, const SBTParams &params=kSBT)
 Half-extent of the frustum envelope in X at a given Z (mm).
 
constexpr double yHalfAt (double z_mm, const SBTParams &params=kSBT)
 Half-extent of the frustum envelope in Y at a given Z (mm).
 
constexpr double zSubLo (int s, const SBTParams &params=kSBT)
 Z of the start of sub-frustum s (mm).
 
constexpr double hbeamFlangeOffset (const SBTParams &params=kSBT)
 Offset of a flange's mid-plane from the beam axis (mm).
 
constexpr double hbeamHalfHeight (const SBTParams &params=kSBT)
 Reach of a flange's outer surface from the beam axis (mm) = h/2.
 
constexpr double zSplitOffset (const SBTParams &params=kSBT)
 Z offset, from the start of a sub-frustum, of the column front-flange outer edge.
 
constexpr double sideContainerHalfThickness (const SBTParams &params=kSBT)
 Half-thickness of a side container in X (mm).
 
constexpr double sideContainerCentreX (double x_half_mm, const SBTParams &params=kSBT)
 |X| of a side container's centroid, given the local frustum half-width.
 
constexpr double sideSensorInnerX (double x_half_mm, const SBTParams &params=kSBT)
 |X| of a side container's innermost face (mm).
 
constexpr double topBottomContainerHalfThickness (const SBTParams &params=kSBT)
 Half-thickness of a top/bottom container in Y (mm).
 
constexpr double topBottomContainerCentreY (double y_half_mm, const SBTParams &params=kSBT)
 |Y| of a top/bottom container's centroid (mm).
 
constexpr double topBottomSensorInnerY (double y_half_mm, const SBTParams &params=kSBT)
 |Y| of a top/bottom container's innermost face (mm).
 
constexpr double topBottomAvailX (double x_half_mm, const SBTParams &params=kSBT)
 Half-extent in X available to top/bottom containers (mm).
 
constexpr double longBeamCentreY (double y_half_mm, const SBTParams &params=kSBT)
 |Y| of a top/bottom longitudinal beam's axis (mm).
 
constexpr double longBeamInnerY (double y_half_mm, const SBTParams &params=kSBT)
 |Y| reached by a longitudinal beam's inner flange surface (mm).
 
constexpr bool isWellFormed (const SBTParams &params=kSBT)
 Are params self-consistent, before asking whether they leave a decay region? Every dimension positive, the helium clearance non-negative, the sensor clearance under half a container thickness and the flanges under half the beam height.
 
constexpr double innerFreeHalfX (double z_mm, const SBTParams &params=kSBT)
 |X| of the innermost SBT material at z_mm (mm).
 
constexpr double innerFreeHalfY (double z_mm, const SBTParams &params=kSBT)
 |Y| of the innermost SBT material at z_mm (mm).
 
constexpr HeliumPiece heliumPieceAt (int i, const SBTParams &params=kSBT)
 Helium slab i, for 0 <= i < 2*nSubFrustum.
 
constexpr bool leavesDecayRegion (const SBTParams &params=kSBT)
 Does params leave a decay region for the helium to fill?
 
constexpr HeliumSlabs heliumSlabs (const SBTParams &params=kSBT)
 The helium stack for arbitrary params.
 
void buildHelium (GeoPhysVol *container, const GeoMaterial *helium, std::span< const HeliumPiece > pieces=kHeliumPieces)
 Place helium slabs into container.
 

Variables

constexpr SBTParams kSBT {}
 The shipped SBT.
 
constexpr double kEnvelopeHalfX = 2200.0
 
constexpr double kEnvelopeHalfY = 3300.0
 
constexpr double kEnvelopeHalfZ = 25200.0
 
constexpr std::string_view kAirMaterial = "Air"
 
constexpr std::string_view kSteelMaterial = "Iron"
 
constexpr std::string_view kWallMaterial = "Aluminium"
 
constexpr std::string_view kScintillatorMaterial = "LAB"
 
constexpr std::string_view kHeliumMaterial = "PressurisedHe90"
 
constexpr auto kHeliumPieces
 The helium slabs of the shipped SBT.
 
constexpr int kMaxSubFrustum = 64
 

Detailed Description

Compile-time parameters of the Surround Background Tagger (SBT).

Drives the steel H-beam supporting structure, the LAB scintillator sensor containers, and the central helium volume of the DecayVolume subsystem. All lengths are raw doubles in mm (GeoModel's native unit). The invariants of these constants are static_asserts at the bottom of this header.

Function Documentation

◆ buildHelium()

void SHiPGeometry::SBT::buildHelium ( GeoPhysVol *  container,
const GeoMaterial *  helium,
std::span< const HeliumPiece >  pieces = kHeliumPieces 
)

Place helium slabs into container.

Call it after SBTStructureBuilder / SBTSensorBuilder — the helium is a consequence of them.

Takes the slabs, not the parameters, and that is deliberate: defaulting to the constexpr kHeliumPieces makes "the shipped geometry is byte-identical" a property of the signature rather than of the optimiser. Deriving the slabs here from an SBTParams would move the arithmetic to run time, where -ffp-contract=fast (GCC's C++ default) may contract a + (z - b) * c into an FMA; constant evaluation never contracts. It would look like a tidy-up and would shift the helium by a ULP.

◆ hbeamFlangeOffset()

constexpr double SHiPGeometry::SBT::hbeamFlangeOffset ( const SBTParams &  params = kSBT)
constexpr

Offset of a flange's mid-plane from the beam axis (mm).

◆ hbeamHalfHeight()

constexpr double SHiPGeometry::SBT::hbeamHalfHeight ( const SBTParams &  params = kSBT)
constexpr

Reach of a flange's outer surface from the beam axis (mm) = h/2.

◆ heliumPieceAt()

constexpr HeliumPiece SHiPGeometry::SBT::heliumPieceAt ( int  i,
const SBTParams &  params = kSBT 
)
constexpr

Helium slab i, for 0 <= i < 2*nSubFrustum.

Each slab is inset from innerFreeHalfX/Y by params.heliumClearance and spans one envelope segment (two per sub-frustum).

This is the single definition of the helium. kHeliumPieces is this function tabulated for kSBT; leavesDecayRegion() walks it without tabulating, which is what lets it answer for an nSubFrustum no array could hold.

◆ heliumSlabs()

constexpr HeliumSlabs SHiPGeometry::SBT::heliumSlabs ( const SBTParams &  params = kSBT)
constexpr

The helium stack for arbitrary params.

A count of 0 means the request was out of range (nSubFrustum outside 1..kMaxSubFrustum); ask leavesDecayRegion() whether a configuration is buildable at all.

◆ innerFreeHalfX()

constexpr double SHiPGeometry::SBT::innerFreeHalfX ( double  z_mm,
const SBTParams &  params = kSBT 
)
constexpr

|X| of the innermost SBT material at z_mm (mm).

Minimum over every volume class that can reach the decay region in X. Currently only the side scintillator containers do; the columns and corner beams sit a further half-flange-width outboard.

◆ innerFreeHalfY()

constexpr double SHiPGeometry::SBT::innerFreeHalfY ( double  z_mm,
const SBTParams &  params = kSBT 
)
constexpr

|Y| of the innermost SBT material at z_mm (mm).

Minimum over every volume class that can reach the decay region in Y: the top/bottom scintillator containers and the inner flange of the top/bottom longitudinal beams, which is the binding one.

◆ isWellFormed()

constexpr bool SHiPGeometry::SBT::isWellFormed ( const SBTParams &  params = kSBT)
constexpr

Are params self-consistent, before asking whether they leave a decay region? Every dimension positive, the helium clearance non-negative, the sensor clearance under half a container thickness and the flanges under half the beam height.

leavesDecayRegion() and both builders check it.

◆ leavesDecayRegion()

constexpr bool SHiPGeometry::SBT::leavesDecayRegion ( const SBTParams &  params = kSBT)
constexpr

Does params leave a decay region for the helium to fill?

False if params are not well formed (isWellFormed() in SBTConstants.h: a non-positive dimension, a negative clearance, containers or beams that come out inside out), or if the beams, containers or clearances have swallowed the frustum. The latter happens in three ways, all covered here:

  • a slab has non-positive half-width (containers wider than the frustum);
  • two knots cross, i.e. a sub-frustum is shorter than the sensors' flat piece — knotAt(2s+1) = zSubLo(s) + zSplitOffset() then overshoots knotAt(2s+2) = zSubLo(s+1), so the slab between them is inverted. This subsumes the zSplitOffset() < subLength() assertion in SBTConstants.h, which is kept only because its message is more specific and because it also constrains SBTSensorBuilder;
  • a negative clearance, which puts the helium inside the SBT by construction and cannot be caught by a degeneracy test — it makes the slabs larger.

Used by the static_assert below for the shipped parameters, and by test_decayvolume for the configurations that must not build.

◆ longBeamCentreY()

constexpr double SHiPGeometry::SBT::longBeamCentreY ( double  y_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

|Y| of a top/bottom longitudinal beam's axis (mm).

◆ longBeamInnerY()

constexpr double SHiPGeometry::SBT::longBeamInnerY ( double  y_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

|Y| reached by a longitudinal beam's inner flange surface (mm).

The beam is inclined by the frustum taper, so its cross-section is rotated: the flange surface lies hbeamHalfHeight()/cos(atan(yGrowth)) from the axis measured in world Y, not hbeamHalfHeight().

◆ nWalls()

constexpr int SHiPGeometry::SBT::nWalls ( const SBTParams &  params = kSBT)
constexpr

Number of aluminium walls per container (nCells + 1).

◆ sideContainerCentreX()

constexpr double SHiPGeometry::SBT::sideContainerCentreX ( double  x_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

|X| of a side container's centroid, given the local frustum half-width.

◆ sideContainerHalfThickness()

constexpr double SHiPGeometry::SBT::sideContainerHalfThickness ( const SBTParams &  params = kSBT)
constexpr

Half-thickness of a side container in X (mm).

◆ sideSensorInnerX()

constexpr double SHiPGeometry::SBT::sideSensorInnerX ( double  x_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

|X| of a side container's innermost face (mm).

◆ subLength()

constexpr double SHiPGeometry::SBT::subLength ( const SBTParams &  params = kSBT)
constexpr

Length of one sub-frustum along Z (mm).

◆ topBottomAvailX()

constexpr double SHiPGeometry::SBT::topBottomAvailX ( double  x_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

Half-extent in X available to top/bottom containers (mm).

The container stops half a flange width short of the frustum wall (that is where the columns' inner face is), less a 1 mm gap so it does not land flush against them. The 1 mm is inherited from the original SBTSensorBuilder and is a literal, not sensorClearance — the two happen to be equal at the current settings, which is worth being aware of when changing sensorClearance, but they are not the same quantity and this one is deliberately left as-is.

◆ topBottomContainerCentreY()

constexpr double SHiPGeometry::SBT::topBottomContainerCentreY ( double  y_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

|Y| of a top/bottom container's centroid (mm).

◆ topBottomContainerHalfThickness()

constexpr double SHiPGeometry::SBT::topBottomContainerHalfThickness ( const SBTParams &  params = kSBT)
constexpr

Half-thickness of a top/bottom container in Y (mm).

◆ topBottomSensorInnerY()

constexpr double SHiPGeometry::SBT::topBottomSensorInnerY ( double  y_half_mm,
const SBTParams &  params = kSBT 
)
constexpr

|Y| of a top/bottom container's innermost face (mm).

◆ webHeight()

constexpr double SHiPGeometry::SBT::webHeight ( const SBTParams &  params = kSBT)
constexpr

Clear web height = height - 2*flange thickness (mm).

◆ xGrowth()

constexpr double SHiPGeometry::SBT::xGrowth ( const SBTParams &  params = kSBT)
constexpr

dx_half/dz of the frustum (dimensionless).

◆ xHalfAt()

constexpr double SHiPGeometry::SBT::xHalfAt ( double  z_mm,
const SBTParams &  params = kSBT 
)
constexpr

Half-extent of the frustum envelope in X at a given Z (mm).

◆ yGrowth()

constexpr double SHiPGeometry::SBT::yGrowth ( const SBTParams &  params = kSBT)
constexpr

dy_half/dz of the frustum (dimensionless).

◆ yHalfAt()

constexpr double SHiPGeometry::SBT::yHalfAt ( double  z_mm,
const SBTParams &  params = kSBT 
)
constexpr

Half-extent of the frustum envelope in Y at a given Z (mm).

◆ zExit()

constexpr double SHiPGeometry::SBT::zExit ( const SBTParams &  params = kSBT)
constexpr

Exit-face Z in the DecayVolume local frame (mm).

◆ zSplitOffset()

constexpr double SHiPGeometry::SBT::zSplitOffset ( const SBTParams &  params = kSBT)
constexpr

Z offset, from the start of a sub-frustum, of the column front-flange outer edge.

Sensor containers are split here: the piece upstream of it must present a flat outer face, or it would eat into the column.

◆ zSubLo()

constexpr double SHiPGeometry::SBT::zSubLo ( int  s,
const SBTParams &  params = kSBT 
)
constexpr

Z of the start of sub-frustum s (mm).

Variable Documentation

◆ kAirMaterial

constexpr std::string_view SHiPGeometry::SBT::kAirMaterial = "Air"
inlineconstexpr

◆ kEnvelopeHalfX

constexpr double SHiPGeometry::SBT::kEnvelopeHalfX = 2200.0
inlineconstexpr

◆ kEnvelopeHalfY

constexpr double SHiPGeometry::SBT::kEnvelopeHalfY = 3300.0
inlineconstexpr

◆ kEnvelopeHalfZ

constexpr double SHiPGeometry::SBT::kEnvelopeHalfZ = 25200.0
inlineconstexpr

◆ kHeliumMaterial

constexpr std::string_view SHiPGeometry::SBT::kHeliumMaterial = "PressurisedHe90"
inlineconstexpr

◆ kHeliumPieces

constexpr auto SHiPGeometry::SBT::kHeliumPieces
inlineconstexpr
Initial value:
= [] {
std::array<HeliumPiece, 2 * kSBT.nSubFrustum> pieces{};
for (int i = 0; i < 2 * kSBT.nSubFrustum; ++i) {
pieces[static_cast<std::size_t>(i)] = heliumPieceAt(i, kSBT);
}
return pieces;
}()
constexpr HeliumPiece heliumPieceAt(int i, const SBTParams &params=kSBT)
Helium slab i, for 0 <= i < 2*nSubFrustum.
Definition SBTEnvelope.h:185
constexpr SBTParams kSBT
The shipped SBT.
Definition SBTConstants.h:75
int nSubFrustum
Definition SBTConstants.h:40

The helium slabs of the shipped SBT.

Exactly sized, and the only stack the geometry ever builds: buildHelium() defaults to it so that nothing on the production path re-derives the helium at run time (see the note on buildHelium).

◆ kMaxSubFrustum

constexpr int SHiPGeometry::SBT::kMaxSubFrustum = 64
inlineconstexpr

◆ kSBT

constexpr SBTParams SHiPGeometry::SBT::kSBT {}
inlineconstexpr

The shipped SBT.

Every primitive below defaults to it, so a call site that does not care about parameterisation reads exactly as it did when these were loose constants.

inline is load-bearing, not decoration: at namespace scope constexpr implies const implies internal linkage, and without inline every translation unit would get its own kSBT — which the inline functions naming it in their default arguments would then quietly violate the ODR over ([basic.def.odr]/14, no diagnostic required).

◆ kScintillatorMaterial

constexpr std::string_view SHiPGeometry::SBT::kScintillatorMaterial = "LAB"
inlineconstexpr

◆ kSteelMaterial

constexpr std::string_view SHiPGeometry::SBT::kSteelMaterial = "Iron"
inlineconstexpr

◆ kWallMaterial

constexpr std::string_view SHiPGeometry::SBT::kWallMaterial = "Aluminium"
inlineconstexpr