97 Gaudi::svcLocator()->service(
"MdcCalibFunSvc", l_mdcCalFunSvc );
106 unsigned nCores = cores.length();
111 for (
int i = 0; i < nCores; i++ )
113 layerid = ( *cores[i]->hit() ).wire()->layerId();
114 if ( layerid >= lyr )
139 for (
int i = 0; i <
t.links().length(); i++ ) { chi2Old = chi2Old +
t.links()[i]->pull(); }
148 double( *d )[5] =
new double[nCores][5];
160 const double ea_init = 0.000001;
177 while ( nTrial < 100 )
182 for (
unsigned j = 0; j < 5; j++ ) dchi2da[j] = 0;
188 for (
unsigned j = 0; j < 5; j++ )
196 while (
TMLink* l = cores[i++] )
200 const HepPoint3D& onTrack = l->positionOnTrack();
201 const HepPoint3D& onWire = l->positionOnWire();
202 d[i - 1][j] = ( onTrack - onWire ).mag();
232 while (
TMLink* l = cores[i++] )
238 std::cout <<
"TrkReco:TRF:: bad wire" << std::endl;
242 const HepPoint3D& onTrack = l->positionOnTrack();
243 const HepPoint3D& onWire = l->positionOnWire();
245 if ( onWire.cross( onTrack ).z() < 0. ) leftRight =
WireHitLeft;
248 if ( ( t0Offset == 0. ) && ( _propagation == 0 ) && ( !_tof ) )
251 distance = l->drift( leftRight );
252 eDistance = h.
dDrift( leftRight );
257 int wire = h.
wire()->
id();
259 int side = leftRight;
260 if ( side == 0 ) side = 0;
262 double tp[3] = { p.x(), p.y(), p.z() };
264 double x[3] = { onWire.x(), onWire.y(), onWire.z() };
265 double tprop = l_mdcCalFunSvc->
getTprop( layerId, onWire.z() * 10. );
267 double T0 = l_mdcCalFunSvc->
getT0( layerId, wirelocal );
268 double drifttime = h.
reccdc()->
tdc -
tof - tprop - timeWalk - T0;
269 l->setDriftTime( drifttime );
272 int prop = _propagation;
273 const double x0 =
t.helix().pivot().x();
274 const double y0 =
t.helix().pivot().y();
275 Hep3Vector pivot_helix( x0, y0, 0 );
276 const double dr =
t.helix().a()[0];
277 const double phi0 =
t.helix().a()[1];
278 const double kappa =
t.helix().a()[2];
279 const double dz =
t.helix().a()[3];
280 const double tanl =
t.helix().a()[4];
282 const double Bz = -1000 * ( getPmgnIMF()->getReferField() );
283 const double alpha = 333.564095 / Bz;
285 const double cox = x0 + dr *
cos( phi0 ) -
alpha *
cos( phi0 ) / kappa;
286 const double coy = y0 + dr *
sin( phi0 ) -
alpha *
sin( phi0 ) / kappa;
287 HepPoint3D dir( onTrack.y() - coy, cox - onTrack.x(), 0 );
288 double pos_phi = onWire.phi();
289 double dir_phi = dir.phi();
290 while ( pos_phi >
pi ) { pos_phi -=
pi; }
291 while ( pos_phi < 0 ) { pos_phi +=
pi; }
292 while ( dir_phi >
pi ) { dir_phi -=
pi; }
293 while ( dir_phi < 0 ) { dir_phi +=
pi; }
294 double entrangle = dir_phi - pos_phi;
295 while ( entrangle >
pi / 2 ) entrangle -=
pi;
296 while ( entrangle < ( -1 ) *
pi / 2 ) entrangle +=
pi;
298 l_mdcCalFunSvc->
driftTimeToDist( drifttime, layerId, wirelocal, side, entrangle );
300 if ( layer == -1 || layerId != layer )
302 edist = l_mdcCalFunSvc->
getSigma( layerId, side, dist, entrangle, tanl,
305 else if ( layerId == layer ) { edist = 99999999; }
307 distance = (double)dist;
308 eDistance = (double)edist;
310 double eDistance2 = eDistance * eDistance;
313 const double d0 = ( onTrack - onWire ).mag();
316 double dDistance = d0 - distance;
319 for (
int j = 0; j < 5; j++ )
321 dDda[j] = ( d[i - 1][j] - d0 ) / ea[j];
326 dchi2da += ( dDistance / eDistance2 ) * dDda;
327 d2chi2d2a += vT_times_v( dDda ) / eDistance2;
328 double pChi2 = dDistance * dDistance / eDistance2;
338 l->update( onTrack, onWire, leftRight, pChi2 );
339 l->drift( distance, 0 );
340 l->drift( distance, 1 );
341 l->dDrift( eDistance, 0 );
342 l->dDrift( eDistance, 1 );
345 else if ( layerId == layer ) { l->distance( ( onTrack - onWire ).mag() ); }
349 double change = chi2Old - chi2;
350 if ( 0 <= change && change < 0.01 )
break;
355 if ( -0.01 < change )
362 else if ( change > 0. )
369 else if ( nTrial == 0 )
378 std::cout <<
"TrkReco:TRF:: bad chi2 = " << chi2 << std::endl;
384 for (
unsigned j = 0; j < 5; j++ ) alpha2[j][j] *= ( 1 + factor );
386 da = solve( alpha2, beta );
399 for ( i = 0; i < 5; i++ )
401 ea[i] = 0.0001 *
abs( da[i] );
402 if ( ea[i] > ea_init ) ea[i] = ea_init;
403 if ( ea[i] < 1.0e-10 ) ea[i] = 1.0e-10;
413 Ea = d2chi2d2a.inverse( err );
416 double y_[6] = { 0, 0, 0, 0, 0, 0 };
420 int nsign = a[2] /
abs( a[2] );
422 a[4] = y_[5] / sqrt( y_[4] * y_[4] + y_[3] * y_[3] );
423 a[2] = nsign * 1 / sqrt( y_[4] * y_[4] + y_[3] * y_[3] );
425 if ( !err && layer == -1 )
431 else if ( !err && layer != -1 )
439 t._ndf = nCores - dim;
443 t.pivot( pivot_bak );
452 double Z( 0. ), A( 0. ), Ionization( 0. ), Density( 0. ), Radlen( 0. );
454 G4LogicalVolume* logicalMdc = 0;
459 G4Material* mdcMaterial = logicalMdc->GetMaterial();
461 for ( i = 0; i < mdcMaterial->GetElementVector()->size(); i++ )
463 Z += ( mdcMaterial->GetElement( i )->GetZ() ) * ( mdcMaterial->GetFractionVector()[i] );
464 A += ( mdcMaterial->GetElement( i )->GetA() ) * ( mdcMaterial->GetFractionVector()[i] );
466 Ionization = mdcMaterial->GetIonisation()->GetMeanExcitationEnergy();
467 Density = mdcMaterial->GetDensity() / ( g / cm3 );
468 Radlen = mdcMaterial->GetRadlen();
469 RkFitMaterial FitMdcMaterial( Z, A / g / mole, Ionization / eV, Density, Radlen / 10. );
470 cout <<
"mdcgas: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
471 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
472 <<
" Radlen: " << Radlen << endl;
477 G4LogicalVolume* innerwallVolume =
const_cast<G4LogicalVolume*
>(
478 GDMLProcessor::GetInstance()->GetLogicalVolume(
"logicalMdcSegment2" ) );
479 G4Material* innerwallMaterial = innerwallVolume->GetMaterial();
480 G4Tubs* innerwallTub =
dynamic_cast<G4Tubs*
>( innerwallVolume->GetSolid() );
484 for ( i = 0; i < innerwallMaterial->GetElementVector()->size(); i++ )
486 Z += ( innerwallMaterial->GetElement( i )->GetZ() ) *
487 ( innerwallMaterial->GetFractionVector()[i] );
488 A += ( innerwallMaterial->GetElement( i )->GetA() ) *
489 ( innerwallMaterial->GetFractionVector()[i] );
492 Ionization = innerwallMaterial->GetIonisation()->GetMeanExcitationEnergy();
493 Density = innerwallMaterial->GetDensity() / ( g / cm3 );
494 Radlen = innerwallMaterial->GetRadlen();
495 cout <<
"Mdc innerwall, Al: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
496 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
497 <<
" Radlen: " << Radlen << endl;
498 RkFitMaterial FitInnerwallMaterial( Z, A / g / mole, Ionization / eV, Density,
503 G4LogicalVolume* logicalBes = 0;
508 G4LogicalVolume* logicalAirVolume =
const_cast<G4LogicalVolume*
>(
509 GDMLProcessor::GetInstance()->GetLogicalVolume(
"logicalWorld" ) );
510 G4Material* airMaterial = logicalAirVolume->GetMaterial();
513 for ( i = 0; i < airMaterial->GetElementVector()->size(); i++ )
515 Z += ( airMaterial->GetElement( i )->GetZ() ) * ( airMaterial->GetFractionVector()[i] );
516 A += ( airMaterial->GetElement( i )->GetA() ) * ( airMaterial->GetFractionVector()[i] );
518 Ionization = airMaterial->GetIonisation()->GetMeanExcitationEnergy();
519 Density = airMaterial->GetDensity() / ( g / cm3 );
520 Radlen = airMaterial->GetRadlen();
521 cout <<
"air: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
522 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
523 <<
" Radlen: " << Radlen << endl;
524 RkFitMaterial FitAirMaterial( Z, A / g / mole, Ionization / eV, Density, Radlen / 10. );
528 G4LogicalVolume* logicalOuterBeVolume =
const_cast<G4LogicalVolume*
>(
529 GDMLProcessor::GetInstance()->GetLogicalVolume(
"logicalouterBe" ) );
530 G4Material* outerBeMaterial = logicalOuterBeVolume->GetMaterial();
532 G4Tubs* outerBeTub =
dynamic_cast<G4Tubs*
>( logicalOuterBeVolume->GetSolid() );
535 for ( i = 0; i < outerBeMaterial->GetElementVector()->size(); i++ )
537 Z += ( outerBeMaterial->GetElement( i )->GetZ() ) *
538 ( outerBeMaterial->GetFractionVector()[i] );
539 A += ( outerBeMaterial->GetElement( i )->GetA() ) *
540 ( outerBeMaterial->GetFractionVector()[i] );
542 Ionization = outerBeMaterial->GetIonisation()->GetMeanExcitationEnergy();
543 Density = outerBeMaterial->GetDensity() / ( g / cm3 );
544 Radlen = outerBeMaterial->GetRadlen();
545 cout <<
"outer beryllium: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
546 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
547 <<
" Radlen: " << Radlen << endl;
548 RkFitMaterial FitOuterBeMaterial( Z, A / g / mole, Ionization / eV, Density, Radlen / 10. );
552 G4LogicalVolume* logicalOilLayerVolume =
const_cast<G4LogicalVolume*
>(
553 GDMLProcessor::GetInstance()->GetLogicalVolume(
"logicaloilLayer" ) );
554 G4Material* oilLayerMaterial = logicalOilLayerVolume->GetMaterial();
555 G4Tubs* oilLayerTub =
dynamic_cast<G4Tubs*
>( logicalOilLayerVolume->GetSolid() );
559 for ( i = 0; i < oilLayerMaterial->GetElementVector()->size(); i++ )
561 Z += ( oilLayerMaterial->GetElement( i )->GetZ() ) *
562 ( oilLayerMaterial->GetFractionVector()[i] );
563 A += ( oilLayerMaterial->GetElement( i )->GetA() ) *
564 ( oilLayerMaterial->GetFractionVector()[i] );
566 Ionization = oilLayerMaterial->GetIonisation()->GetMeanExcitationEnergy();
567 Density = oilLayerMaterial->GetDensity() / ( g / cm3 );
568 Radlen = oilLayerMaterial->GetRadlen();
569 cout <<
"cooling oil: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
570 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
571 <<
" Radlen: " << Radlen << endl;
572 RkFitMaterial FitOilLayerMaterial( Z, A / g / mole, Ionization / eV, Density, Radlen / 10. );
576 G4LogicalVolume* logicalInnerBeVolume =
const_cast<G4LogicalVolume*
>(
577 GDMLProcessor::GetInstance()->GetLogicalVolume(
"logicalinnerBe" ) );
579 G4Material* innerBeMaterial = logicalInnerBeVolume->GetMaterial();
580 G4Tubs* innerBeTub =
dynamic_cast<G4Tubs*
>( logicalInnerBeVolume->GetSolid() );
583 for ( i = 0; i < innerBeMaterial->GetElementVector()->size(); i++ )
585 Z += ( innerBeMaterial->GetElement( i )->GetZ() ) *
586 ( innerBeMaterial->GetFractionVector()[i] );
587 A += ( innerBeMaterial->GetElement( i )->GetA() ) *
588 ( innerBeMaterial->GetFractionVector()[i] );
590 Ionization = innerBeMaterial->GetIonisation()->GetMeanExcitationEnergy();
591 Density = innerBeMaterial->GetDensity() / ( g / cm3 );
592 Radlen = innerBeMaterial->GetRadlen();
593 cout <<
"inner beryllium: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
594 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
595 <<
" Radlen: " << Radlen << endl;
596 RkFitMaterial FitInnerBeMaterial( Z, A / g / mole, Ionization / eV, Density, Radlen / 10. );
600 G4LogicalVolume* logicalGoldLayerVolume =
const_cast<G4LogicalVolume*
>(
601 GDMLProcessor::GetInstance()->GetLogicalVolume(
"logicalgoldLayer" ) );
602 G4Material* goldLayerMaterial = logicalGoldLayerVolume->GetMaterial();
603 G4Tubs* goldLayerTub =
dynamic_cast<G4Tubs*
>( logicalGoldLayerVolume->GetSolid() );
607 for ( i = 0; i < goldLayerMaterial->GetElementVector()->size(); i++ )
609 Z += ( goldLayerMaterial->GetElement( i )->GetZ() ) *
610 ( goldLayerMaterial->GetFractionVector()[i] );
611 A += ( goldLayerMaterial->GetElement( i )->GetA() ) *
612 ( goldLayerMaterial->GetFractionVector()[i] );
614 Ionization = goldLayerMaterial->GetIonisation()->GetMeanExcitationEnergy();
615 Density = goldLayerMaterial->GetDensity() / ( g / cm3 );
616 Radlen = goldLayerMaterial->GetRadlen();
617 cout <<
"gold layer: Z: " << Z <<
" A: " << ( A / ( g / mole ) )
618 <<
" Ionization: " << ( Ionization / eV ) <<
" Density: " << Density
619 <<
" Radlen: " << Radlen << endl;
620 RkFitMaterial FitGoldLayerMaterial( Z, A / g / mole, Ionization / eV, Density,
625 double radius, thick, length, z0;
628 radius = innerwallTub->GetInnerRadius() / ( cm );
629 thick = innerwallTub->GetOuterRadius() / (cm)-innerwallTub->GetInnerRadius() / ( cm );
630 length = 2.0 * innerwallTub->GetZHalfLength() / ( cm );
632 cout <<
"innerwall: "
633 <<
" radius: " << radius <<
" thick:" << thick <<
" length: " << length << endl;
639 radius = outerBeTub->GetOuterRadius() / ( cm );
640 thick = innerwallTub->GetInnerRadius() / (cm)-outerBeTub->GetOuterRadius() / ( cm );
641 length = 2.0 * innerwallTub->GetZHalfLength() / ( cm );
643 cout <<
"outer air: "
644 <<
" radius: " << radius <<
" thick:" << thick <<
" length: " << length << endl;
649 radius = outerBeTub->GetInnerRadius() / ( cm );
650 thick = outerBeTub->GetOuterRadius() / (cm)-outerBeTub->GetInnerRadius() / ( cm );
651 length = 2.0 * outerBeTub->GetZHalfLength() / ( cm );
654 <<
" radius: " << radius <<
" thick:" << thick <<
" length: " << length << endl;
659 radius = oilLayerTub->GetInnerRadius() / ( cm );
660 thick = oilLayerTub->GetOuterRadius() / (cm)-oilLayerTub->GetInnerRadius() / ( cm );
661 length = 2.0 * oilLayerTub->GetZHalfLength() / ( cm );
663 cout <<
"oil layer: "
664 <<
" radius: " << radius <<
" thick:" << thick <<
" length: " << length << endl;
669 radius = innerBeTub->GetInnerRadius() / ( cm );
670 thick = innerBeTub->GetOuterRadius() / (cm)-innerBeTub->GetInnerRadius() / ( cm );
671 length = 2.0 * innerBeTub->GetZHalfLength() / ( cm );
674 <<
" radius: " << radius <<
" thick:" << thick <<
" length: " << length << endl;
679 radius = goldLayerTub->GetInnerRadius() / ( cm );
680 thick = goldLayerTub->GetOuterRadius() / (cm)-goldLayerTub->GetInnerRadius() / ( cm );
681 length = 2.0 * goldLayerTub->GetZHalfLength() / ( cm );
683 cout <<
"gold layer: "
684 <<
" radius: " << radius <<
" thick:" << thick <<
" length: " << length << endl;