Xyce  6.1
N_ANP_HB.C
Go to the documentation of this file.
1 //-----------------------------------------------------------------------------
2 // Copyright Notice
3 //
4 // Copyright 2002 Sandia Corporation. Under the terms
5 // of Contract DE-AC04-94AL85000 with Sandia Corporation, the U.S.
6 // Government retains certain rights in this software.
7 //
8 // Xyce(TM) Parallel Electrical Simulator
9 // Copyright (C) 2002-2015 Sandia Corporation
10 //
11 // This program is free software: you can redistribute it and/or modify
12 // it under the terms of the GNU General Public License as published by
13 // the Free Software Foundation, either version 3 of the License, or
14 // (at your option) any later version.
15 //
16 // This program is distributed in the hope that it will be useful,
17 // but WITHOUT ANY WARRANTY; without even the implied warranty of
18 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 // GNU General Public License for more details.
20 //
21 // You should have received a copy of the GNU General Public License
22 // along with this program. If not, see <http://www.gnu.org/licenses/>.
23 //-----------------------------------------------------------------------------
24 
25 //-----------------------------------------------------------------------------
26 // Filename : $RCSfile: N_ANP_HB.C,v $
27 // Purpose : HB analysis functions.
28 // Special Notes :
29 // Creator : Todd Coffey, 1414, Ting Mei, 1437
30 // Creation Date : 07/23/08
31 //
32 // Revision Information:
33 // ---------------------
34 // Revision Number: $Revision: 1.194 $
35 // Revision Date : $Date: 2015/09/23 14:18:12 $
36 // Current Owner : $Author: dgbaur $
37 //-----------------------------------------------------------------------------
38 #include <Xyce_config.h>
39 
40 #include <N_ANP_AnalysisManager.h>
41 #include <N_ANP_DCSweep.h>
42 #include <N_ANP_HB.h>
43 #include <N_ANP_OutputMgrAdapter.h>
44 #include <N_ANP_Report.h>
45 #include <N_ANP_Transient.h>
46 #include <N_DEV_DeviceMgr.h>
47 #include <N_IO_ActiveOutput.h>
48 #include <N_IO_CircuitBlock.h>
49 #include <N_IO_CmdParse.h>
50 #include <N_IO_OptionBlock.h>
51 #include <N_IO_PkgOptionsMgr.h>
52 #include <N_IO_SpiceSeparatedFieldTool.h>
53 #include <N_LAS_BlockSystemHelpers.h>
54 #include <N_LAS_BlockVector.h>
55 #include <N_LAS_HBBuilder.h>
56 #include <N_LAS_HBPrecondFactory.h>
57 #include <N_LAS_PrecondFactory.h>
58 #include <N_LAS_System.h>
59 #include <N_LOA_HBLoader.h>
61 #include <N_NLS_Manager.h>
62 #include <N_PDS_ParMap.h>
63 #include <N_TIA_DataStore.h>
65 #include <N_TIA_StepErrorControl.h>
67 #include <N_UTL_APFT.h>
68 #include <N_UTL_Diagnostic.h>
69 #include <N_UTL_ExtendedString.h>
70 #include <N_UTL_FFTInterface.hpp>
71 #include <N_UTL_FeatureTest.h>
72 #include <N_UTL_MachDepParams.h>
73 #include <N_UTL_Math.h>
74 #include <N_UTL_Timer.h>
75 
76 #include <Teuchos_BLAS.hpp>
77 #include <Teuchos_Utils.hpp>
78 #include <Teuchos_ScalarTraits.hpp>
79 #include <Teuchos_SerialDenseMatrix.hpp>
80 #include <Teuchos_SerialDenseVector.hpp>
81 #include <Teuchos_SerialDenseHelpers.hpp>
82 #include <Teuchos_SerialDenseSolver.hpp>
83 
84 #include <N_PDS_Comm.h>
85 
86 using Teuchos::rcp;
87 using Teuchos::RCP;
88 using Teuchos::rcp_dynamic_cast;
89 
90 namespace Xyce {
91 namespace Analysis {
92 
93 //-----------------------------------------------------------------------------
94 // Function : HB::HB( AnalysisManager * )
95 // Purpose :
96 // Special Notes :
97 // Scope : public
98 // Creator : Todd Coffey, SNL
99 // Creation Date : 09/18/2008
100 //-----------------------------------------------------------------------------
102  AnalysisManager & analysis_manager,
103  Linear::System & linear_system,
104  Nonlinear::Manager & nonlinear_manager,
105  Loader::Loader & loader,
106  Device::DeviceMgr & device_manager,
107  Linear::Builder & builder,
108  Topo::Topology & topology,
109  IO::InitialConditionsManager & initial_conditions_manager,
110  IO::RestartMgr & restart_manager)
111  : AnalysisBase(analysis_manager, "HB"),
112  StepEventListener(&analysis_manager),
113  analysisManager_(analysis_manager),
114  loader_(loader),
115  linearSystem_(linear_system),
116  nonlinearManager_(nonlinear_manager),
117  deviceManager_(device_manager),
118  builder_(builder),
119  topology_(topology),
120  initialConditionsManager_(initial_conditions_manager),
121  restartManager_(restart_manager),
122  hbLoaderPtr_(0),
123  hbBuilderPtr_(),
124  hbLinearSystem_(0),
125  isPaused(false),
126  startDCOPtime(0.0),
127  endTRANtime(0.0),
128  isTransient_(false),
129  test_(false),
130  size_(21),
131  freqs_(),
132  freqsGiven_(false),
133  period_(1.0),
134  startUpPeriods_(0),
135  startUpPeriodsGiven_(false),
136  saveIcData_(false),
137  precFactory_(0),
138  taHB_(1),
139  numTimePts_(0),
140  voltLimFlag_(1),
141  intmodMax_(0),
142  method_("APFT"),
143  intmodMaxGiven_(false),
144  fastTimeDisc_(N_MPDE_Discretization::Backward),
145  fastTimeDiscOrder_(1),
146  resetForStepCalledBefore_(false)
147 {
149 }
150 
151 //-----------------------------------------------------------------------------
152 // Function : HB::~HB
153 // Purpose :
154 // Special Notes :
155 // Scope : public
156 // Creator :
157 // Creation Date :
158 //-----------------------------------------------------------------------------
160 {
161  delete hbLoaderPtr_;
162  delete hbLinearSystem_;
163  delete precFactory_;
164 }
165 
166 //-----------------------------------------------------------------------------
167 // Function : HB::notify
168 // Purpose :
169 // Special Notes :
170 // Scope : public
171 // Creator : Dave Baur
172 // Creation Date :
173 //-----------------------------------------------------------------------------
174 void HB::notify(const StepEvent &event)
175 {
176  if (event.state_ == StepEvent::STEP_STARTED)
177  {
179 
181  {
182  goodSolutionVec_.clear();
183  goodStateVec_.clear();
184  goodQVec_.clear();
185  goodStoreVec_.clear();
186 
188 
192 
193  // un-set the fast source flag in the devices
194  std::vector<std::string> srcVec;
196 
198 
200  deviceManager_.setMPDEFlag( false );
201 
210  topology_);
211 
214 
215  analysisManager_.getXyceTranTimer().resetStartTime();
216  }
217 
219  }
220 }
221 
222 //-----------------------------------------------------------------------------
223 // Function : HB::getDoubleDCOPStep
224 // Purpose :
225 // Special Notes :
226 // Scope : public
227 // Creator : Eric Keiter
228 // Creation Date : 3/24/2014
229 //-----------------------------------------------------------------------------
231 {
234  else
235  return 0;
236 }
237 
238 //-----------------------------------------------------------------------------
239 // Function : HB::getDCOPFlag
240 // Purpose :
241 // Special Notes :
242 // Scope : public
243 // Creator : Eric Keiter
244 // Creation Date : 3/24/2014
245 //-----------------------------------------------------------------------------
246 bool HB::getDCOPFlag() const
247 {
250 
251  // DCSweep is a special case in the HB analysis type. The HB calculation is
252  // performed through a DC analysis object. However, this function (getDCOPFlag)
253  // is called (ultimately) from the device package to determine a bunch of
254  // state-dependent load decisions. For an HB calculation, it should NOT
255  // do a DCOP load. It needs to do a full transient load.
256  else
257  return false;
258 }
259 
260 //-----------------------------------------------------------------------------
261 // Function : HB::run()
262 // Purpose :
263 // Special Notes :
264 // Scope : public
265 // Creator : Todd Coffey, SNL
266 // Creation Date : 09/18/2008
267 //-----------------------------------------------------------------------------
268 bool HB::doRun()
269 {
270  return doInit() && doLoopProcess() && doFinish();
271 }
272 
273 //-----------------------------------------------------------------------------
274 // Function : HB::init()
275 // Purpose :
276 // Special Notes :
277 // Scope : public
278 // Creator : Todd Coffey, SNL
279 // Creation Date : 09/18/2008
280 //-----------------------------------------------------------------------------
282 {
283  Xyce::lout() << " ***** Running HB initial conditions....\n" << std::endl;
284 
285  if (DEBUG_HB)
286  Xyce::dout() << std::endl
287  << section_divider << std::endl
288  << " HB::init()" << std::endl;
289 
291 
292  setFreqPoints_();
293 
294  period_ = 1.0/freqPoints_[(size_ - 1)/2 + 1];
295 
296  if (DEBUG_HB)
297  Xyce::dout() << "HB period =" << period_ << std::endl;
298 
299  fastTimes_.resize(size_);
300 
301  goodTimePoints_.resize(size_);
302 
303  if (freqs_.size() == 1)
304  {
305  double TimeStep = period_/size_;
306  timeSteps_.push_back( TimeStep );
307 
308  for( int i = 0; i < size_; ++i )
309  {
310  fastTimes_[i] = i*TimeStep;
311  }
312  }
313  else
314  {
315  setTimePoints_();
316  }
317 
319 
320  setInitialGuess();
321 
323 
324  // now that we have size_, continue with the initialization of objects for HB
325  mpdeDiscPtr_ = rcp(new N_MPDE_Discretization(fastTimeDisc_, fastTimeDiscOrder_));
326  hbBuilderPtr_ = rcp(new Linear::HBBuilder(size_, mpdeDiscPtr_));
327 
328  if (DEBUG_HB)
329  Xyce::dout() << "HB::init(): Generate Maps\n";
330 
331  hbBuilderPtr_->generateMaps( rcp(pdsMgrPtr_->getParallelMap( Parallel::SOLUTION ), false),
332  rcp(pdsMgrPtr_->getParallelMap( Parallel::SOLUTION_OVERLAP_GND ), false) );
333  hbBuilderPtr_->generateStateMaps( rcp(pdsMgrPtr_->getParallelMap( Parallel::STATE ),false) );
334  hbBuilderPtr_->generateStoreMaps( rcp(pdsMgrPtr_->getParallelMap( Parallel::STORE ),false) );
335  hbBuilderPtr_->generateLeadCurrentMaps( rcp(pdsMgrPtr_->getParallelMap( Parallel::LEADCURRENT ),false) );
336  hbBuilderPtr_->generateGraphs( *pdsMgrPtr_->getMatrixGraph( Parallel::JACOBIAN ));
337 
338  HBICVectorPtr_ = hbBuilderPtr_->createTimeDomainBlockVector();
339  HBICStateVectorPtr_ = hbBuilderPtr_->createTimeDomainStateBlockVector();
340  HBICStoreVectorPtr_ = hbBuilderPtr_->createTimeDomainStoreBlockVector();
341  HBICQVectorPtr_ = hbBuilderPtr_->createTimeDomainBlockVector();
342 
343  HBICVectorFreqPtr_ = hbBuilderPtr_->createExpandedRealFormTransposeBlockVector();
344 
345  // set the fast source flag in the devices
346  std::vector<std::string> srcVec;
347  deviceManager_.registerFastSources(pdsMgrPtr_->getPDSComm()->comm(), srcVec );
348 
349  //nonlinearManager_.getHBOptions(saved_nlHBOB_);
350 
351  // Create HB Loader.
352  delete hbLoaderPtr_;
355  hbLoaderPtr_->registerAppLoader( rcp(&loader_, false) );
356 
357  // Create DFT for HB Loader
358  // NOTE: For single-tone HB the DFT will probably be a FFT, for multi-tone a specialized
359  // implementation of the Util::DFTInterfaceDecl will need to be made and registered with
360  // the HB loader.
361 
362  ftInData_.resize( size_ );
363  ftOutData_.resize( size_ +1 );
364  iftInData_.resize( size_ +1 );
365  iftOutData_.resize( size_ );
366  if (freqs_.size() == 1)
367  {
368  if (ftInterface_ == Teuchos::null)
369  {
370  ftInterface_ = Teuchos::rcp( new N_UTL_FFTInterface<std::vector<double> >( size_ ) );
371  ftInterface_->registerVectors( ftInData_, &ftOutData_, iftInData_, &iftOutData_ );
372  }
373  else if (ftInterface_->getFFTInterface()->getSignalLength() != size_)
374  {
375  ftInterface_ = Teuchos::rcp( new N_UTL_FFTInterface<std::vector<double> >( size_ ) );
376  ftInterface_->registerVectors( ftInData_, &ftOutData_, iftInData_, &iftOutData_ );
377  }
378  hbLoaderPtr_->registerDFTInterface( ftInterface_->getFFTInterface() );
379  }
380  else
381  {
382  createFT_();
383 
384  dftInterface_ = Teuchos::rcp( new N_UTL_APFT<std::vector<double> >( idftMatrix_, dftMatrix_ ) );
385  dftInterface_->registerVectors( Teuchos::rcp( &ftInData_, false ), Teuchos::rcp( &ftOutData_, false ), Teuchos::rcp( &iftInData_, false ), Teuchos::rcp( &iftOutData_, false ) );
387  }
388 
389  if (taHB_==1)
390  {
391  // Pick up IC data from the initial transient.
392  for (int i=0 ; i<size_ ; ++i)
393  {
394  if (DEBUG_HB && isActive(Diag::HB_FAST_TIMES))
395  Xyce::dout() << "HB::init(): Loading initial condition data from time: fastTimes_["
396  << i << "] = " << fastTimes_[i] << std::endl;
397 
398  HBICVectorPtr_->block(i) = *(goodSolutionVec_[i]);
399  HBICStateVectorPtr_->block(i) = *(goodStateVec_[i]);
400  HBICQVectorPtr_->block(i) = *(goodQVec_[i]);
401  HBICStoreVectorPtr_->block(i) = *(goodStoreVec_[i]);
402  }
403 
405 
406  }
407 
408  if (DEBUG_HB && isActive(Diag::HB_PRINT_VECTORS))
409  {
410  Xyce::dout() << "HB Initial Condition Solution!\n";
411  HBICVectorPtr_->printPetraObject(std::cout);
412  Xyce::dout() << "HB Initial Condition State Vector!\n";
413  HBICStateVectorPtr_->printPetraObject(std::cout);
414  Xyce::dout() << "HB Initial Condition Store Vector!\n";
415  HBICStoreVectorPtr_->printPetraObject(std::cout);
416  }
417 
418  //Destroy Solvers, etc. from IC phase and prepare for HB
419  //-----------------------------------------
420 
422 
423  deviceManager_.setMPDEFlag( true );
425 
426  //-----------------------------------------
427 
428  //Finish setup of HB Loader
429  //-----------------------------------------
430  goodTimePoints_.resize(size_+1);
432 
433 
435 
437 
438  //-----------------------------------------
439  //Construct Solvers, etc. for HB Phase
440  //-----------------------------------------
441  delete hbLinearSystem_;
442  hbLinearSystem_ = new Linear::System();
443  //-----------------------------------------
444 
445  //hack needed by TIA initialization currently
446  hbBuilderPtr_->registerPDSManager( pdsMgrPtr_ );
447  hbLinearSystem_->registerPDSManager( pdsMgrPtr_ );
448  hbLinearSystem_->registerBuilder( &*hbBuilderPtr_ );
449 
450  hbLinearSystem_->initializeSystem();
451 
454 
455  // Let the HB loader know that the application of the operator is matrix free
457 
458  if (!precFactory_)
459  {
460  // Generate the HB preconditioner factory.
461  precFactory_ = new Linear::HBPrecondFactory(saved_lsHBOB_, builder_);
462  }
463 
464  // Register application loader with preconditioner factory
465  precFactory_->registerHBLoader( rcp(hbLoaderPtr_, false) );
466  precFactory_->registerHBBuilder( hbBuilderPtr_ );
467  precFactory_->setFastTimes( goodTimePoints_ );
468  precFactory_->setTimeSteps( timeSteps_ );
469  precFactory_->setHBFreqs( freqPoints_ );
470 
472 
473  //Initialization of Solvers, etc. for HB Phase
475 
477 
479 
482 
483  if (DEBUG_HB)
484  {
485  Xyce::dout() << section_divider << std::endl;
486  }
487 
488  return true;
489 
490 }
491 
492 //-----------------------------------------------------------------------------
493 // Function : HB::loopProcess()
494 // Purpose :
495 // Special Notes :
496 // Scope : public
497 // Creator : Todd Coffey, SNL
498 // Creation Date : 09/18/2008
499 //-----------------------------------------------------------------------------
501 {
502  bool returnValue = true;
503 
504  Xyce::lout() << " ***** Beginning full HB simulation....\n" << std::endl;
505 
506  if (DEBUG_HB)
507  {
508  Xyce::dout() << std::endl
509  << section_divider << std::endl
510  << " HB::loopProcess" << std::endl;
511  }
512 
514  *(dsPtr->nextSolutionPtr) = *(HBICVectorFreqPtr_.get());
515  *(dsPtr->nextStatePtr) = *(HBICStateVectorPtr_.get());
516  *(dsPtr->nextStorePtr) = *(HBICStoreVectorPtr_.get());
517 
518  // try to run the problem
519  {
520  Xyce::IO::ActiveOutput x(analysisManager_.getOutputManagerAdapter().getOutputManager());
521  x.add(Xyce::IO::PrintType::HB, ANP_MODE_HB);
522 
524  currentAnalysisObject_ = &dc_sweep;
526  returnValue = dc_sweep.run();
527 
528  // Add in simulation times
529  accumulateStatistics_(dc_sweep);
530 
531  // print out analysis info
532  Xyce::lout() << " ***** Harmonic Balance Computation Summary *****" << std::endl;
533  dc_sweep.printLoopInfo( 0, 0 );
534 
536 
538  }
539 
540  if (DEBUG_HB)
541  {
542  dout() << section_divider << std::endl;
543  }
544 
545  return returnValue;
546 }
547 
548 //-----------------------------------------------------------------------------
549 // Function : HB::processSuccessfulDCOP()
550 // Purpose :
551 // Special Notes :
552 // Scope : public
553 // Creator : Todd Coffey, SNL
554 // Creation Date : 09/18/2008
555 //-----------------------------------------------------------------------------
557 {
558  return false;
559 }
560 
561 //-----------------------------------------------------------------------------
562 // Function : HB::processSuccessfulStep()
563 // Purpose :
564 // Special Notes :
565 // Scope : public
566 // Creator : Todd Coffey, SNL
567 // Creation Date : 09/18/2008
568 //-----------------------------------------------------------------------------
570 {
571  return false;
572 }
573 
574 //-----------------------------------------------------------------------------
575 // Function : HB::processFailedStep
576 // Purpose :
577 // Special Notes :
578 // Scope : public
579 // Creator : Todd Coffey, SNL
580 // Creation Date : 09/18/2008
581 //-----------------------------------------------------------------------------
583 {
584  return false;
585 }
586 
587 //-----------------------------------------------------------------------------
588 // Function : HB::processFailedDCOP
589 // Purpose :
590 // Special Notes :
591 // Scope : public
592 // Creator : Todd Coffey, SNL
593 // Creation Date : 09/18/2008
594 //-----------------------------------------------------------------------------
596 {
597  return false;
598 }
599 
600 //-----------------------------------------------------------------------------
601 // Function : HB::finish
602 // Purpose :
603 // Special Notes :
604 // Scope : public
605 // Creator : Todd Coffey, SNL
606 // Creation Date : 09/18/2008
607 //-----------------------------------------------------------------------------
609 {
611 
612  return true;
613 }
614 
616 {
617  return true;
618 }
619 
620 //-----------------------------------------------------------------------------
621 // Function : HB::finalVerboseOutput
622 // Purpose :
623 // Special Notes :
624 // Scope : public
625 // Creator : Todd Coffey, SNL
626 // Creation Date : 09/18/2008
627 //-----------------------------------------------------------------------------
629 {
630  return false;
631 }
632 
633 //-----------------------------------------------------------------------------
634 // Function : AnalysisManager::setHBAnalysisParams
635 // Purpose : Sets the HB sweep calculation parameters (from .HB)
636 // Special Notes :
637 // Scope : public
638 // Creator : Todd Coffey, Ting Mei
639 // Creation Date : 7/30/08
640 //-----------------------------------------------------------------------------
641 bool
643  const Util::OptionBlock & option_block)
644 {
645  for (Util::ParamList::const_iterator it = option_block.begin(), end = option_block.end(); it != end; ++it)
646  {
647  if ((*it).uTag() == "FREQ")
648  {
649  freqs_ = (*it).getValue<std::vector<double> >();
650  freqsGiven_ = true;
651  }
652  }
653 
654  if (freqs_[0] <= 0.0 )
655  {
656  Report::UserError() << "Frequency of oscillation " << freqs_[0] << " is less than or equal to zero, invalid .HB specification";
657  }
658 
659  if (DEBUG_ANALYSIS && isActive(Diag::TIME_PARAMETERS))
660  {
661  dout() << section_divider << std::endl
662  << "HB transient simulation parameters"
663  //<< Util::push << std::endl
664  << std::endl
665  << "HB frequency = " << freqs_[0] << std::endl
666  //<< Util::pop << std::endl;
667  << std::endl;
668  }
669 
670  return true;
671 }
672 
673 
674 //-----------------------------------------------------------------------------
675 // Function : HB::setHBIntParams
676 // Purpose :
677 // Special Notes :
678 // Scope : public
679 // Creator : Heidi Thornquist
680 // Creation Date : 05/13/13
681 //-----------------------------------------------------------------------------
682 bool HB::setHBIntParams(const Util::OptionBlock & OB)
683 {
684  for(Util::ParamList::const_iterator iterPL = OB.begin(), endPL = OB.end(); iterPL != endPL; ++iterPL )
685  {
686  ExtendedString tag = iterPL->tag();
687  tag.toUpper();
688 
689  if (std::string(tag,0,7) == "NUMFREQ" )
690  {
691 
692  size_ = iterPL->getImmutableValue<int>() *2 + 1;
693 
694  numFreqs_.push_back(size_);
695  }
696  else if ( tag == "STARTUPPERIODS" )
697  {
698  startUpPeriods_ = iterPL->getImmutableValue<int>();
699 
700  if (startUpPeriods_ > 0)
701  startUpPeriodsGiven_ = true;
702  }
703  else if( tag == "SAVEICDATA" )
704  {
705  saveIcData_ = true;
706  }
707  else if( tag == "TEST" )
708  {
709  test_ = static_cast<bool> (iterPL->getImmutableValue<int>());
710  }
711  else if (tag == "DEBUGLEVEL" )
712  {
713  setHBDebugLevel(iterPL->getImmutableValue<int>());
714  }
715  else if ( tag == "TAHB" )
716  {
717  taHB_ = iterPL->getImmutableValue<int>();
718  }
719  else if ( tag == "VOLTLIM" )
720  {
721  voltLimFlag_ = static_cast<bool> (iterPL->getImmutableValue<int>());
722  }
723  else if ( tag == "INTMODMAX" )
724  {
725  intmodMax_ = iterPL->getImmutableValue<int>();
726 
727  if ( intmodMax_ > 0)
728  intmodMaxGiven_ = true;
729  }
730  else if ( tag == "METHOD" )
731  {
732  ExtendedString stringVal ( iterPL->stringValue() );
733  stringVal.toUpper();
734  method_ = stringVal;
735  }
736 
737  else if ( tag == "NUMTPTS")
738  {
739  numTimePts_ = iterPL->getImmutableValue<int>();
740  }
741  else
742  {
743  UserWarning(*this) << "Unrecognized HBINT option " << tag;
744  }
745  }
746 
747  if (numFreqs_.size() != 0 && numFreqs_.size() != freqs_.size() )
748  {
749  Report::UserError() << "The size of numFreq does not match the number of tones in .hb!";
750  }
751 
752 
753  if (numFreqs_.size() == 0 )
754  {
755 
756  numFreqs_.resize( freqs_.size() ) ;
757  for (int i=0; i < freqs_.size(); i++ )
758  {
759  numFreqs_[i] = size_;
760  }
761 
762  }
763 
764  return true;
765 }
766 
767 //-----------------------------------------------------------------------------
768 // Function : HB::setLinSol
769 // Purpose : this is needed for .STEP to work with HB
770 // Special Notes :
771 // Scope : public
772 // Creator : Eric R. Keiter
773 // Creation Date : 7/12/2013
774 //-----------------------------------------------------------------------------
775 bool HB::setLinSol(const Util::OptionBlock & OB)
776 {
777  // Save the non-HB linear solver option block
778  saved_lsOB_ = OB;
779 
780  return true;
781 }
782 
783 //-----------------------------------------------------------------------------
784 // Function : HB::setHBLinSol
785 // Purpose :
786 // Special Notes :
787 // Scope : public
788 // Creator : Heidi Thornquist
789 // Creation Date : 5/13/13
790 //-----------------------------------------------------------------------------
791 bool HB::setHBLinSol(const Util::OptionBlock & OB, Linear::Builder &builder)
792 {
793  // Save the HB linear solver option block
794  saved_lsHBOB_ = OB;
795 
796  // Generate the HB preconditioner factory.
797  precFactory_ = new Linear::HBPrecondFactory(OB, builder);
798 
799  return true;
800 }
801 
802 //-----------------------------------------------------------------------------
803 // Function : HB::isAnalysis
804 // Purpose :
805 // Special Notes :
806 // Scope : public
807 // Creator : Heidi Thornquist
808 // Creation Date : 5/13/13
809 // Notes : Alternatively, we could try to cast the analysis object
810 // : However, this method is called a lot.
811 //-----------------------------------------------------------------------------
812 bool HB::isAnalysis( int analysis_type ) const
813 {
814  return analysis_type == ANP_MODE_TRANSIENT && isTransient_;
815 }
816 
817 //-----------------------------------------------------------------------------
818 // Function : HB::prepareHBOutput
819 // Purpose :
820 // Special Notes :
821 // Scope : public
822 // Creator : Eric Keiter, 9233, Computational Sciences
823 // Creation Date : 08/20/07
824 //-----------------------------------------------------------------------------
826  Linear::Vector & solnVecPtr,
827  std::vector<double> & timePoints,
828  std::vector<double> & freqPoints,
829  RCP<Linear::BlockVector> & timeDomainSolnVec,
830  RCP<Linear::BlockVector> & freqDomainSolnVecReal,
831  RCP<Linear::BlockVector> & freqDomainSolnVecImag,
832  RCP<Linear::BlockVector> & timeDomainStoreVec,
833  RCP<Linear::BlockVector> & freqDomainStoreVecReal,
834  RCP<Linear::BlockVector> & freqDomainStoreVecImag,
835  RCP<Linear::BlockVector> & timeDomainLeadCurrentVec,
836  RCP<Linear::BlockVector> & freqDomainLeadCurrentVecReal,
837  RCP<Linear::BlockVector> & freqDomainLeadCurrentVecImaginary,
838  RCP<Linear::BlockVector> & timeDomainJunctionVoltageVec,
839  RCP<Linear::BlockVector> & freqDomainJunctionVoltageVecReal,
840  RCP<Linear::BlockVector> & freqDomainJunctionVoltageVecImaginary
841  )
842 {
843  Linear::BlockVector & blockSolVecPtr = dynamic_cast<Linear::BlockVector &>(solnVecPtr);
844 // int tdsampleRate = tdsampleRate_;
845 
846  if ( numTimePts_ < size_ )
847  numTimePts_ = size_ ;
848  if ( numTimePts_ % 2 == 0)
849  numTimePts_ = numTimePts_ + 1;
850 
851  int blockCounttd = numTimePts_;
852 
853  // int blockCounttd = (size_-1)/2*tdsampleRate*2 + 1;
854 
855  int N = blockSolVecPtr.blockCount();
856  Teuchos::RCP<N_PDS_ParMap> baseMap = Teuchos::rcp_const_cast<N_PDS_ParMap>( hbBuilderPtr_->getBaseSolutionMap() );
857  Teuchos::RCP<N_PDS_ParMap> globalMap = Linear::createBlockParMap( blockCounttd, *baseMap );
858 
859  timeDomainSolnVec = Teuchos::rcp( new Linear::BlockVector(blockCounttd, globalMap, baseMap ) );
860 
861  Teuchos::RCP<Linear::BlockVector> bStoreVecFreqPtr_ = hbLoaderPtr_->getStoreVecFreqPtr();
862  Teuchos::RCP<Linear::BlockVector> bLeadCurrentVecFreqPtr_ = hbLoaderPtr_->getLeadCurrentVecFreqPtr();
863  freqPoints = freqPoints_;
864 
865  timePoints.resize(blockCounttd);
866 
867  if (numTimePts_== size_ )
868  {
869  timePoints = fastTimes_;
870  }
871 
872  else
873  {
874 
875  double TimeStep = period_/blockCounttd;
876 
877  for( int i = 0; i < blockCounttd; ++i )
878  timePoints[i] = i*TimeStep;
879 
880  ftInData_.resize( blockCounttd);
881  ftOutData_.resize( blockCounttd +1 );
882  iftInData_.resize( blockCounttd +1 );
883  iftOutData_.resize( blockCounttd);
884 
885 
886  if (freqs_.size() == 1 )
887  {
888  if (ftInterface_->getFFTInterface()->getSignalLength() != blockCounttd)
889  {
890  ftInterface_ = Teuchos::rcp( new N_UTL_FFTInterface<std::vector<double> >(blockCounttd) );
891  ftInterface_->registerVectors( ftInData_, &ftOutData_, iftInData_, &iftOutData_ );
892 
893  hbLoaderPtr_->registerDFTInterface( ftInterface_->getFFTInterface() );
894  }
895 
896  }
897  else
898  {
899  updateIFT_( timePoints);
900  iftInData_.resize( size_+1 );
901 
902  dftInterface_ = Teuchos::rcp( new N_UTL_APFT<std::vector<double> >( idftMatrix_, dftMatrix_ ) );
903  dftInterface_->registerVectors( Teuchos::rcp( &ftInData_, false ), Teuchos::rcp( &ftOutData_, false ), Teuchos::rcp( &iftInData_, false ), Teuchos::rcp( &iftOutData_, false ) );
905 
906  }
907  }
908 
909 // Create individual block vectors to store the real and imaginary parts separately.
910 // Teuchos::RCP<N_PDS_ParMap> baseMap = Teuchos::rcp_const_cast<N_PDS_ParMap>( hbBuilderPtr_->getBaseSolutionMap() );
911 
912 
913  int blockCount = size_;
914  Teuchos::RCP<N_PDS_ParMap> globalMapfreq = Linear::createBlockParMap( blockCount, *baseMap );
915  freqDomainSolnVecReal = Teuchos::rcp( new Linear::BlockVector( blockCount, globalMapfreq, baseMap ) );
916  freqDomainSolnVecImag = Teuchos::rcp( new Linear::BlockVector( blockCount, globalMapfreq, baseMap ) );
917 
918  hbLoaderPtr_->permutedIFT(blockSolVecPtr, &*timeDomainSolnVec, numTimePts_);
919 
920  // Now copy over the frequency domain solution, real and imaginary parts separately, into the output vectors.
921 
922  for (int j=0; j<N; j++)
923  {
924  // See if this time-domain solution variable is owned by the local processor.
925  // If so, this processor owns the entire j-th block of the blockSolVecPtr vector,
926  // and the j-th entry of every block in the freqDomainSo
927  // lnVec[Real/Imag] vector.
928  int lid = baseMap->globalToLocalIndex( j );
929  Linear::Vector& solBlock = blockSolVecPtr.block( j );
930 
931  Linear::Vector& realVecRef = freqDomainSolnVecReal->block((blockCount-1)/2);
932  Linear::Vector& imagVecRef = freqDomainSolnVecImag->block((blockCount-1)/2);
933 
934  if (lid >= 0)
935  {
936  realVecRef[lid] = solBlock[0];
937  imagVecRef[lid] = solBlock[1];
938  }
939 
940  for (int i=1; i <= (size_-1)/2; ++i)
941 // for (int i=1; i <= (blockCount-1)/2; ++i)
942  {
943  Linear::Vector& realVecRef_neg = freqDomainSolnVecReal->block((blockCount-1)/2 - i);
944  Linear::Vector& imagVecRef_neg = freqDomainSolnVecImag->block((blockCount-1)/2 - i);
945  Linear::Vector& realVecRef_pos = freqDomainSolnVecReal->block((blockCount-1)/2 + i);
946  Linear::Vector& imagVecRef_pos = freqDomainSolnVecImag->block((blockCount-1)/2 + i);
947 
948  if (lid >= 0)
949  {
950  realVecRef_neg[lid] = solBlock[ 2*(size_-i) ];
951  imagVecRef_neg[lid] = solBlock[ 2*(size_-i) + 1 ];
952  realVecRef_pos[lid] = solBlock[ 2*i ];
953  imagVecRef_pos[lid] = solBlock[ 2*i+1 ];
954  }
955  }
956  }
957 
958  // proceed to store variables
959  Teuchos::RCP<N_PDS_ParMap> baseStoreMap = Teuchos::rcp_const_cast<N_PDS_ParMap>( hbBuilderPtr_->getBaseStoreMap() );
960  Teuchos::RCP<N_PDS_ParMap> globalStoreMap = Linear::createBlockParMap( blockCounttd, *baseStoreMap );
961  Teuchos::RCP<N_PDS_ParMap> globalStoreMapfd = Linear::createBlockParMap( blockCount, *baseStoreMap );
962 
963  freqDomainStoreVecReal = Teuchos::rcp( new Linear::BlockVector( blockCount, globalStoreMapfd, baseStoreMap ) );
964  freqDomainStoreVecImag = Teuchos::rcp( new Linear::BlockVector( blockCount, globalStoreMapfd, baseStoreMap ) );
965 
966  timeDomainStoreVec = Teuchos::rcp( new Linear::BlockVector( blockCounttd, globalStoreMap, baseStoreMap ) );
967  N = timeDomainStoreVec->block(0).globalLength();
968 
969  for (int j=0; j<N; j++)
970  {
971  // See if this time-domain solution variable is owned by the local processor.
972  // If so, this processor owns the entire j-th block of the blockSolVecPtr vector,
973  // and the j-th entry of every block in the freqDomainSolnVec[Real/Imag] vector.
974  int lid = baseStoreMap->globalToLocalIndex( j );
975  Linear::Vector& storeBlock = bStoreVecFreqPtr_->block( j );
976 
977  Linear::Vector& realVecRef = freqDomainStoreVecReal->block((blockCount-1)/2);
978  Linear::Vector& imagVecRef = freqDomainStoreVecImag->block((blockCount-1)/2);
979 
980  if (lid >= 0)
981  {
982  realVecRef[lid] = storeBlock[0];
983  imagVecRef[lid] = storeBlock[1];
984  }
985 
986  for (int i=1; i <= (size_-1)/2; ++i)
987  {
988  Linear::Vector& realVecRef_neg = freqDomainStoreVecReal->block((blockCount-1)/2 - i);
989  Linear::Vector& imagVecRef_neg = freqDomainStoreVecImag->block((blockCount-1)/2 - i);
990  Linear::Vector& realVecRef_pos = freqDomainStoreVecReal->block((blockCount-1)/2 + i);
991  Linear::Vector& imagVecRef_pos = freqDomainStoreVecImag->block((blockCount-1)/2 + i);
992 
993  if (lid >= 0)
994  {
995  realVecRef_neg[lid] = storeBlock[ 2*(size_ -i) ];
996  imagVecRef_neg[lid] = storeBlock[ 2*(size_ -i) + 1 ];
997  realVecRef_pos[lid] = storeBlock[ 2*i ];
998  imagVecRef_pos[lid] = storeBlock[ 2*i+1 ];
999  }
1000  }
1001  }
1002 
1003 
1004  //
1005  if (bStoreVecFreqPtr_->blockCount() > 0 )
1006  {
1007  hbLoaderPtr_->permutedIFT(*bStoreVecFreqPtr_, &*timeDomainStoreVec, numTimePts_);
1008  }
1009 
1010  // lead current vector
1011  Teuchos::RCP<N_PDS_ParMap> baseLeadCurrentMap = Teuchos::rcp_const_cast<N_PDS_ParMap>( hbBuilderPtr_->getBaseLeadCurrentMap() );
1012  Teuchos::RCP<N_PDS_ParMap> globalLeadCurrentMap = Linear::createBlockParMap( blockCounttd, *baseLeadCurrentMap );
1013  Teuchos::RCP<N_PDS_ParMap> globalLeadCurrentMapfq = Linear::createBlockParMap( blockCount, *baseLeadCurrentMap );
1014 
1015  freqDomainLeadCurrentVecReal = Teuchos::rcp( new Linear::BlockVector( blockCount, globalLeadCurrentMapfq, baseLeadCurrentMap ) );
1016  freqDomainLeadCurrentVecImaginary = Teuchos::rcp( new Linear::BlockVector( blockCount, globalLeadCurrentMapfq, baseLeadCurrentMap ) );
1017  freqDomainJunctionVoltageVecReal = Teuchos::rcp( new Linear::BlockVector( blockCount, globalLeadCurrentMapfq, baseLeadCurrentMap ) );
1018  freqDomainJunctionVoltageVecImaginary = Teuchos::rcp( new Linear::BlockVector( blockCount, globalLeadCurrentMapfq, baseLeadCurrentMap ) );
1019 
1020  timeDomainLeadCurrentVec = Teuchos::rcp( new Linear::BlockVector( blockCounttd, globalLeadCurrentMap, baseLeadCurrentMap ));
1021  timeDomainJunctionVoltageVec = Teuchos::rcp( new Linear::BlockVector( blockCounttd, globalLeadCurrentMap, baseLeadCurrentMap ) );
1022 
1023  N = timeDomainLeadCurrentVec->block(0).globalLength();
1024 
1025  for (int j=0; j<N; j++)
1026  {
1027  // See if this time-domain solution variable is owned by the local processor.
1028  // If so, this processor owns the entire j-th block of the blockSolVecPtr vector,
1029  // and the j-th entry of every block in the freqDomainSolnVec[Real/Imag] vector.
1030  int lid = baseLeadCurrentMap->globalToLocalIndex( j );
1031  Linear::Vector& leadCurrentBlock = bLeadCurrentVecFreqPtr_->block( j );
1032 
1033  Linear::Vector& realVecRef1 = freqDomainLeadCurrentVecReal->block((blockCount-1)/2);
1034  Linear::Vector& imagVecRef1 = freqDomainLeadCurrentVecImaginary->block((blockCount-1)/2);
1035  Linear::Vector& realVecRef2 = freqDomainJunctionVoltageVecReal->block((blockCount-1)/2);
1036  Linear::Vector& imagVecRef2 = freqDomainJunctionVoltageVecImaginary->block((blockCount-1)/2);
1037 
1038  if (lid >= 0)
1039  {
1040  realVecRef1[lid] = leadCurrentBlock[0];
1041  imagVecRef1[lid] = leadCurrentBlock[1];
1042  realVecRef2[lid] = leadCurrentBlock[0];
1043  imagVecRef2[lid] = leadCurrentBlock[1];
1044  }
1045 
1046  for (int i=1; i <= (size_ -1)/2; ++i)
1047  {
1048  Linear::Vector& realVecRef_neg1 = freqDomainLeadCurrentVecReal->block((blockCount-1)/2 - i);
1049  Linear::Vector& imagVecRef_neg1 = freqDomainLeadCurrentVecImaginary->block((blockCount-1)/2 - i);
1050  Linear::Vector& realVecRef_pos2 = freqDomainLeadCurrentVecReal->block((blockCount-1)/2 + i);
1051  Linear::Vector& imagVecRef_pos2 = freqDomainLeadCurrentVecImaginary->block((blockCount-1)/2 + i);
1052 
1053  Linear::Vector& realVecRef_neg3 = freqDomainJunctionVoltageVecReal->block((blockCount-1)/2 - i);
1054  Linear::Vector& imagVecRef_neg3 = freqDomainJunctionVoltageVecImaginary->block((blockCount-1)/2 - i);
1055  Linear::Vector& realVecRef_pos4 = freqDomainJunctionVoltageVecReal->block((blockCount-1)/2 + i);
1056  Linear::Vector& imagVecRef_pos4 = freqDomainJunctionVoltageVecImaginary->block((blockCount-1)/2 + i);
1057 
1058  if (lid >= 0)
1059  {
1060  realVecRef_neg1[lid] = leadCurrentBlock[ 2*(size_ -i) ];
1061  imagVecRef_neg1[lid] = leadCurrentBlock[ 2*(size_ -i) + 1 ];
1062  realVecRef_pos2[lid] = leadCurrentBlock[ 2*i ];
1063  imagVecRef_pos2[lid] = leadCurrentBlock[ 2*i+1 ];
1064  realVecRef_neg3[lid] = leadCurrentBlock[ 2*(size_ -i) ];
1065  imagVecRef_neg3[lid] = leadCurrentBlock[ 2*(size_ -i) + 1 ];
1066  realVecRef_pos4[lid] = leadCurrentBlock[ 2*i ];
1067  imagVecRef_pos4[lid] = leadCurrentBlock[ 2*i+1 ];
1068  }
1069  }
1070  }
1071 
1072  if (bLeadCurrentVecFreqPtr_->blockCount() > 0 )
1073  {
1074  hbLoaderPtr_->permutedIFT(*bLeadCurrentVecFreqPtr_, &*timeDomainLeadCurrentVec, numTimePts_);
1075  }
1076 
1077  if (DEBUG_HB)
1078  {
1079  freqDomainSolnVecReal->printPetraObject(std::cout);
1080  freqDomainSolnVecImag->printPetraObject(std::cout);
1081 
1082  Xyce::dout() << "HB Store Vector FD" << std::endl;
1083 
1084  freqDomainStoreVecReal->printPetraObject(std::cout);
1085  freqDomainStoreVecImag->printPetraObject(std::cout);
1086  }
1087 }
1088 
1089 
1090 //-----------------------------------------------------------------------------
1091 // Function : HB::accumulateStatistics()
1092 // Purpose : Add in the statistics from the current analysis object
1093 // Special Notes :
1094 // Scope : private
1095 // Creator : Heidi Thornquist, 1355, Electrical Models & Simulation
1096 // Creation Date : 05/29/13
1097 //-----------------------------------------------------------------------------
1099 {
1100  hbStatCounts_ += analysis.stats_;
1101 }
1102 
1103 //-----------------------------------------------------------------------------
1104 // Function : HB::setFreqPoints_
1105 // Purpose : Set frequency spectrum for HB analysis.
1106 // Special Notes :
1107 // Scope : private
1108 // Creator : Ting Mei, SNL
1109 // Creation Date : 03/03/2014
1110 //-----------------------------------------------------------------------------
1112 {
1113  if ( !intmodMaxGiven_)
1114  {
1115  int maxValue = 0;
1116  if (numFreqs_.size() != 0 )
1117  // find the max of numFreqs
1118  {
1119  maxValue = (numFreqs_[0] - 1)/2;
1120  for (int i=1; i<numFreqs_.size(); ++i)
1121  {
1122  if ((numFreqs_[i] - 1)/2 > maxValue)
1123  maxValue = (numFreqs_[i] - 1)/2 ;
1124  }
1125  }
1126  else
1127  {
1128  maxValue = (size_ - 1)/2;
1129  }
1130  intmodMax_ = maxValue;
1131  }
1132 
1133  std::vector<int> k;
1134 
1135  int numAnalysisFreqs = freqs_.size();
1136 
1137  numPosFreqs.resize(numAnalysisFreqs);
1138 
1139  k.resize(numAnalysisFreqs);
1140 
1141  k[0] = 1;
1142 
1143  if (numFreqs_.size() != 0 )
1144  numPosFreqs[0] = (numFreqs_[0] - 1)/2;
1145  else
1146  numPosFreqs[0]= (size_ - 1)/2;
1147 
1148  int numTotalFrequencies;
1149 
1150  int numExtraFreqs = 0;
1151 
1152  if (numPosFreqs[0] > intmodMax_)
1153  {
1154  numExtraFreqs += ( numPosFreqs[0] - intmodMax_ );
1155  numFreqs_[0] = (intmodMax_*2 + 1);
1156  }
1157 
1158  numTotalFrequencies = numFreqs_[0];
1159 
1160  for (int i=1; i < numAnalysisFreqs; i++)
1161  {
1162  numPosFreqs[i] = (numFreqs_[i] - 1)/2;
1163 
1164  if (numPosFreqs[i] > intmodMax_)
1165  {
1166  numExtraFreqs += ( numPosFreqs[i] - intmodMax_ );
1167  numFreqs_[i] = (intmodMax_*2 + 1);
1168  }
1169 
1170  k[i] = k[i-1] * numFreqs_[i -1 ];
1171 
1172  numTotalFrequencies *= numFreqs_[i];
1173  }
1174 
1175  if (DEBUG_HB)
1176  {
1177  for (int i=0; i< numAnalysisFreqs; i++)
1178  {
1179  Xyce::dout() << "HB index " << i << std::endl;
1180  Xyce::dout() << "HB numPosFreqs =" << numPosFreqs[i] << std::endl;
1181  Xyce::dout() << "HB k =" << k[i] << std::endl;
1182  }
1183  Xyce::dout() << "HB numTotalFrequencies =" << numTotalFrequencies<< std::endl;
1184  Xyce::dout() << "HB numextrafreqs =" << numExtraFreqs << std::endl;
1185  }
1186 
1187  int numIndex = numTotalFrequencies;
1188 
1189  Teuchos::SerialDenseMatrix<int,double> indexMatrix(numAnalysisFreqs, numTotalFrequencies);
1190 
1191  if (DEBUG_HB)
1192  {
1193  Xyce::dout() << "HB intmodMax =" << intmodMax_ << std::endl;
1194  }
1195 
1196  int nextIndex;
1197 
1198  int idxMod, idxValues;
1199  int sumIndex;
1200 
1201  std::vector<int> goodIndex;
1202  for (int i=0; i < numIndex; i++) // column
1203  {
1204  nextIndex = i;
1205  sumIndex = 0;
1206 
1207  for (int j= (numAnalysisFreqs - 1); j >= 0; j-- ) // row
1208  {
1209  idxMod = nextIndex%k[j];
1210  idxValues = (nextIndex - idxMod)/k[j];
1211 
1212  indexMatrix (j, i) = static_cast<double>(idxValues - (numFreqs_[j] - 1)/2 );
1213  nextIndex = idxMod;
1214  sumIndex += abs(idxValues - (numFreqs_[j] - 1)/2 );
1215 
1216  }
1217 
1218  if( sumIndex <= intmodMax_)
1219  goodIndex.push_back(i);
1220  }
1221 
1222  int diaindexSize = goodIndex.size();
1223 
1224  Teuchos::SerialDenseMatrix<int,double> diaindexMatrix( numAnalysisFreqs, (diaindexSize + numExtraFreqs) );
1225  diaindexMatrix.putScalar(0.0);
1226 
1227  for (int i=0; i < diaindexSize; i++)
1228  {
1229  for (int j= (numAnalysisFreqs - 1); j >= 0; j-- )
1230  diaindexMatrix (j, i) = indexMatrix (j, goodIndex[i]);
1231  }
1232 
1233  if (DEBUG_HB)
1234  {
1235  for (int i=0; i< diaindexSize; i++)
1236  {
1237  dout() << "good index i = " << i << goodIndex[i] << std::endl;
1238  }
1239  dout() << " checking diamond indexMatrix" << std::endl;
1240  diaindexMatrix.print(dout());
1241 
1242  dout() << " checking indexMatrix" << std::endl;
1243  indexMatrix.print(dout());
1244  }
1245 
1246 
1247  int extraIndexPos = diaindexSize;
1248  for (int i=0; i < numAnalysisFreqs ; i++) // column
1249  {
1250 
1251  if (numPosFreqs[i] > intmodMax_)
1252  {
1253 
1254  for (int j=0; j < (numPosFreqs[i] - intmodMax_ ) ; j++)
1255  diaindexMatrix (i, extraIndexPos + j ) = static_cast<double>(intmodMax_ + j + 1 );
1256 
1257  extraIndexPos += (numPosFreqs[i] - intmodMax_ );
1258  }
1259  }
1260 
1261 
1262  if (DEBUG_HB)
1263  {
1264  dout() << " checking diamond indexMatrix after axis" << std::endl;
1265  diaindexMatrix.print(dout());
1266  }
1267 
1268 // get the positive frequencies
1269 
1270  std::vector<double> posfreqPoints_;
1271 
1272  int posindexSize = (diaindexSize - 1)/2;
1273  posfreqPoints_.resize(posindexSize + numExtraFreqs);
1274 
1275  Teuchos::SerialDenseMatrix<int,double> currindexMatrix( Teuchos::View, diaindexMatrix, numAnalysisFreqs, (posindexSize + numExtraFreqs), 0, posindexSize+1 );
1276  Teuchos::SerialDenseVector<int,double> currfreqPoints( Teuchos::View, &posfreqPoints_[0], (posindexSize + numExtraFreqs ) );
1277 
1278  Teuchos::SerialDenseVector<int,double> hbFreqs( Teuchos::View, &freqs_[0], numAnalysisFreqs);
1279 // Teuchos::SerialDenseVector<int,double> currWeightVector( Teuchos::View, &weightVector[i], oversampleRate*size_-(i+1) );
1280  currfreqPoints.multiply( Teuchos::TRANS, Teuchos::NO_TRANS, 1.0, currindexMatrix, hbFreqs, 0.0 );
1281 
1282 
1283  if (DEBUG_HB)
1284  {
1285  dout() << "checking positive frequencies" << std::endl;
1286  currindexMatrix.print(dout());
1287  hbFreqs.print(dout());
1288  currfreqPoints.print(dout());
1289  }
1290 
1291  for (int i=0; i < posindexSize; i++)
1292  {
1293  if (posfreqPoints_[i] < 0.0)
1294  posfreqPoints_[i] = fabs( posfreqPoints_[i]);
1295  }
1296 
1297  std::sort(posfreqPoints_.begin(), posfreqPoints_.end() );
1298 
1299 
1300  if (DEBUG_HB)
1301  {
1302  for (int i=0; i< posfreqPoints_.size(); i++)
1303  dout() << "pos frequency point " << posfreqPoints_[i] << std::endl;
1304  }
1305 
1306  posfreqPoints_.erase(std::unique(posfreqPoints_.begin(), posfreqPoints_.end() ), posfreqPoints_.end() );
1307 
1308 
1309  if (abs( posfreqPoints_[0]) < 2.0*Util::MachineDependentParams::MachinePrecision() )
1310  posfreqPoints_.erase( posfreqPoints_.begin());
1311 
1312  size_ = ( posfreqPoints_.size() ) *2 + 1;
1313 
1314  if (DEBUG_HB)
1315  {
1316  for (int i=0; i<posfreqPoints_.size(); i++)
1317  {
1318  dout() << "pos frequency point after " << posfreqPoints_[i] << std::endl;
1319  }
1320 
1321  Xyce::dout() << "HB size =" << size_ << std::endl;
1322  }
1323 
1324  int i=0;
1325  freqPoints_.resize(size_);
1326 
1327  for( i = 0; i < size_; ++i )
1328  {
1329  if (i < (size_-1)/2)
1330  freqPoints_[i] = - posfreqPoints_[ (size_-1)/2 - i - 1 ];
1331  else if (i > (size_-1)/2)
1332  freqPoints_[i] = posfreqPoints_[ i - (size_-1)/2 - 1 ];
1333  else
1334  freqPoints_[i] = 0.0;
1335  }
1336 
1337  if (DEBUG_HB)
1338  {
1339  for (int i=0; i<freqPoints_.size(); i++)
1340  {
1341  dout() << " frequency point " << freqPoints_[i] << std::endl;
1342  }
1343  }
1344 
1345  return true;
1346 }
1347 
1348 //-----------------------------------------------------------------------------
1349 // Function : HB::setTimePoints_
1350 // Purpose : Set time points for multi-tone HB analysis.
1351 // Special Notes :
1352 // Scope : private
1353 // Creator : Heidi Thornquist and Ting Mei, SNL
1354 // Creation Date : 03/05/2014
1355 //-----------------------------------------------------------------------------
1357 {
1358  // NOTE: Need to make this parallel safe.
1359 
1360  // Resize fastTimes_ vector to be ready to receive from root processor.
1361  fastTimes_.resize (size_);
1362 
1363  int posFreq = (size_-1)/2;
1364  int oversampleRate = 5;
1365 // int periodSampleMultiplier = 3;
1366  int periodSampleMultiplier = 1;
1367 
1368  Teuchos::BLAS<int,double> blas;
1369  std::vector<double> testPoints(oversampleRate*size_);
1370 
1371  int myPID = pdsMgrPtr_->getPDSComm()->procID();
1372 
1373  if (myPID == 0)
1374  {
1375 
1376  for (int i=0; i<oversampleRate*size_; ++i)
1377  {
1378  testPoints[i] = periodSampleMultiplier*period_*((Teuchos::ScalarTraits<double>::random()+1)/2);
1379  }
1380 
1381  Teuchos::SerialDenseMatrix<int,double> testMatrix(size_,oversampleRate*size_);
1382  // NOTE: i represents frequency, j represents sample time
1383  // Set DC values first.
1384  for (int j=0; j<oversampleRate*size_; ++j)
1385  {
1386  testMatrix(0,j) = 1.0;
1387  }
1388  // Set rest of frequency values
1389  for (int i=1; i<=posFreq; i++)
1390  {
1391 // for (int j=0; j<oversampleRate*size_; j+2)
1392  for (int j=0; j<oversampleRate*size_; j++)
1393  {
1394  testMatrix(2*i-1,j) = cos(2*M_PI*freqPoints_[posFreq+i]*testPoints[j]);
1395  testMatrix(2*i,j) = sin(2*M_PI*freqPoints_[posFreq+i]*testPoints[j]);
1396  }
1397  }
1398 
1399  // Now for orthogonalization (yipeee)
1400  std::vector<double> weightVector(oversampleRate*size_);
1401  for (int i=0; i<size_; ++i)
1402  {
1403  // Find column with largest norm, choose as next vector for orthogonalization
1404  int maxIndex = 0;
1405  double maxValue = 0.0;
1406  for (int j=i; j<oversampleRate*size_; ++j)
1407  {
1408  Teuchos::SerialDenseMatrix<int,double> tempVector( Teuchos::View, testMatrix, size_, 1, 0, j );
1409  weightVector[j] = tempVector.normFrobenius();
1410 
1411  if (weightVector[j] > maxValue)
1412  {
1413  maxIndex = j;
1414  maxValue = weightVector[j];
1415  }
1416  }
1417 
1418 
1419  // Swap time and vector.
1420  std::swap( testPoints[i], testPoints[maxIndex] );
1421  Teuchos::SerialDenseVector<int,double> newSwapVector2 = Teuchos::getCol<int,double>( Teuchos::Copy, testMatrix, maxIndex );
1422  Teuchos::SerialDenseVector<int,double> newSwapVector = Teuchos::getCol<int,double>( Teuchos::View, testMatrix, i );
1423  Teuchos::setCol<int,double>( newSwapVector, maxIndex, testMatrix );
1424  Teuchos::setCol<int,double>( newSwapVector2, i, testMatrix );
1425 
1426 // dout() << "Checking testMatrix for i= " << i << std::endl;
1427 // testMatrix.print(dout());
1428 
1429  // Compute inner product with vector from last time point with rest of time points
1430  Teuchos::SerialDenseMatrix<int,double> currTestMatrix( Teuchos::View, testMatrix, size_, oversampleRate*size_-(i+1), 0, i+1 );
1431  Teuchos::SerialDenseVector<int,double> currWeightVector( Teuchos::View, &weightVector[i+1], oversampleRate*size_-(i+1) );
1432 // Teuchos::SerialDenseVector<int,double> currWeightVector( Teuchos::View, &weightVector[i], oversampleRate*size_-(i+1) );
1433  currWeightVector.multiply( Teuchos::TRANS, Teuchos::NO_TRANS, 1.0, currTestMatrix, newSwapVector, 0.0 );
1434 
1435 // dout() << "The current norm is" << std::endl;
1436 // currWeightVector.print(dout());
1437 
1438  // Subtract off scaled vector from rest of time points.
1439  // NOTE: maxValue is the norm of the last time point.
1440  for (int j=i+1; j<oversampleRate*size_; ++j)
1441  {
1442  Teuchos::SerialDenseMatrix<int,double> currVector( Teuchos::View, testMatrix, size_, 1, 0, j );
1443  blas.AXPY( size_, -(currWeightVector[j-(i+1)]/(maxValue*maxValue) ), newSwapVector.values(), 1, currVector.values(), 1 );
1444  }
1445 
1446 
1447  }
1448 // dout() << "Checking testMatrix after orthogonalization." << std::endl;
1449 // testMatrix.print(dout());
1450 
1451  // Sort the chosen test points and then copy them into the fastTimes_ vector.
1452  std::sort( testPoints.begin(), testPoints.begin()+size_ );
1453 
1454  for (int i=0; i<size_; ++i)
1455  {
1456  fastTimes_[i] = testPoints[i];
1457  }
1458  }
1459 
1460  // Communicate testPoints to all processors (broadcast)
1461  pdsMgrPtr_->getPDSComm()->bcast( &fastTimes_[0], size_, 0 );
1462 
1463 
1464  return true;
1465 }
1466 
1467 //-----------------------------------------------------------------------------
1468 // Function : HB::createFT_
1469 // Purpose : Create the DFT and IFT matrices using the time points for multi-tone HB analysis.
1470 // Special Notes :
1471 // Scope : private
1472 // Creator : Heidi Thornquist and Ting Mei, SNL
1473 // Creation Date : 03/05/2014
1474 //-----------------------------------------------------------------------------
1476 {
1477  int posFreq = (size_-1)/2;
1478  idftMatrix_.reshape(size_,size_);
1479 
1480  // NOTE: i represents frequency, j represents sample time
1481  // Set DC values first.
1482  for (int i=0; i<size_; ++i)
1483  {
1484  idftMatrix_(i,0) = 1.0;
1485  }
1486 
1487  // Set rest of frequency values
1488  for (int i=0; i<size_; i++)
1489  {
1490  for (int j=1; j<=posFreq; j++)
1491  {
1492  idftMatrix_(i,2*j-1) = cos(2*M_PI*freqPoints_[posFreq+j]*fastTimes_[i]);
1493  idftMatrix_(i,2*j) = sin(2*M_PI*freqPoints_[posFreq+j]*fastTimes_[i]);
1494  }
1495 
1496  }
1497 
1498  // Compute DFT matrix.
1500  Teuchos::SerialDenseSolver<int,double> ftSolver;
1501  ftSolver.setMatrix( Teuchos::rcp( &dftMatrix_, false ) );
1502  ftSolver.invert();
1503 
1504  return true;
1505 }
1506 
1507 //-----------------------------------------------------------------------------
1508 // Function : HB::setInitialGuess_
1509 // Purpose : Set initial guess for HB analysis.
1510 // Special Notes :
1511 // Scope : private
1512 // Creator : Ting Mei, SNL
1513 // Creation Date : 03/03/2014
1514 //-----------------------------------------------------------------------------
1516 {
1517  bool success = true;
1518 
1519  if (taHB_ == 1)
1520  {
1521  TimeIntg::TIAParams tia_params;
1522 
1523  tia_params.initialTime = 0;
1524  tia_params.finalTime = 1.0/freqs_[0];
1526  tia_params.maxOrder = 1;
1527 
1528  bool retTol1 = runTol(tia_params);
1529  success = success && retTol1;
1530 
1531  // Start up periods need to be run before the initial condition is computed, otherwise
1532  // just used the solution from the tolerance calculation.
1534  {
1535  // set DAE initial time = 0.0
1536  tia_params.initialTime = 0.0;
1537  tia_params.finalTime = startUpPeriods_/freqs_[0];
1538  tia_params.maxOrder = 5;
1540 
1541  bool startupPeriodsSuccess = runStartupPeriods(tia_params);
1542  if (!startupPeriodsSuccess)
1543  {
1544  Report::UserError() << "Failed to calculate the startup periods";
1545  return false;
1546  }
1547 
1548  success = success && startupPeriodsSuccess;
1549 
1550  tia_params.initialTime = startUpPeriods_/freqs_[0]; ;
1551  tia_params.finalTime = tia_params.initialTime + 1.0/freqs_[0];
1553  tia_params.maxOrder = 1;
1554 
1555  bool icSuccess = runTransientIC(tia_params);
1556  if (!icSuccess)
1557  {
1558  Report::UserError() << "Initial HB Transient failed";
1559  return false;
1560  }
1561  success = success && icSuccess;
1562 
1563  deviceManager_.setMPDEFlag( false );
1564  }
1565 
1566  interpolateIC(tia_params.initialTime);
1567  }
1568 
1569  return success;
1570 }
1571 
1572 
1573  //-----------------------------------------------------------------------------
1574 // Function : HB::updateIFT_
1575 // Purpose : Create the IFT matrices using the time points for multi-tone HB analysis.
1576 // Special Notes :
1577 // Scope : private
1578 // Creator : Ting Mei, SNL
1579 // Creation Date : 07/2/2015
1580 //-----------------------------------------------------------------------------
1581 bool HB::updateIFT_( std::vector<double> & tPoints)
1582 {
1583  int posFreq = (size_-1)/2;
1584  // idftMatrix_.reshape(size_,size_);
1585 
1586  int ntpt = tPoints.size();
1587  idftMatrix_.reshape( ntpt, size_);
1588 
1589  // NOTE: i represents frequency, j represents sample time
1590  // Set DC values first.
1591  for (int i=0; i<ntpt; ++i)
1592  {
1593  idftMatrix_(i,0) = 1.0;
1594  }
1595 
1596  // Set rest of frequency values
1597  for (int i=0; i< ntpt; i++)
1598  {
1599  for (int j=1; j<=posFreq; j++)
1600  {
1601  idftMatrix_(i,2*j-1) = cos(2*M_PI*freqPoints_[posFreq+j]* tPoints[i]);
1602  idftMatrix_(i,2*j) = sin(2*M_PI*freqPoints_[posFreq+j]*tPoints[i]);
1603  }
1604  }
1605 
1606 
1607  return true;
1608 }
1609 
1610 //-----------------------------------------------------------------------------
1611 // Function : HB::runTol
1612 // Purpose : Conducts transient run to determine right tolerance
1613 // parameters for IC calculation
1614 // Special Notes :
1615 // Scope : private
1616 // Creator : T. Mei, 1437, Electrical and Micro Modeling
1617 // Creation Date : 02/23/09
1618 //-----------------------------------------------------------------------------
1619 bool
1621  TimeIntg::TIAParams & tia_params)
1622 {
1623  Xyce::lout() << " ***** Computing tolerance parameters for HB IC calculation....\n" << std::endl;
1624 
1625  // Create a transient analysis object for this section.
1626  int numPoints = 0;
1627  {
1628  Xyce::IO::ActiveOutput x(analysisManager_.getOutputManagerAdapter().getOutputManager());
1629  if (!startUpPeriodsGiven_)
1630  x.add(Xyce::IO::PrintType::HB_IC, ANP_MODE_HB);
1631 
1632  isTransient_ = true;
1634  currentAnalysisObject_ = &transient;
1635  analysisManager_.pushActiveAnalysis(&transient);
1636  transient.setTIAParams(tia_params);
1637  transient.setAnalysisParams(Util::OptionBlock());
1638  transient.setSaveTimeSteps(!startUpPeriodsGiven_);
1639  transient.resetForHB();
1640  nonlinearManager_.resetAll(Nonlinear::DC_OP);
1641  analysisManager_.getStepErrorControl().resetAll(tia_params);
1642  analysisManager_.getDataStore()->resetAll(tia_params.absErrorTol, tia_params.relErrorTol);
1643  analysisManager_.setNextOutputTime(0.0);
1644 
1645  {
1646  if (!transient.run())
1647  {
1648  Report::UserError() << "Calculation of tolerance parameters failed for relErrorTol = " << tia_params.relErrorTol;
1649  return false;
1650  }
1651  }
1652 
1653  numPoints = transient.getStepNumber();
1654 
1655  // Add in simulation times
1656  accumulateStatistics_(transient);
1657 
1658  analysisManager_.popActiveAnalysis();
1659  currentAnalysisObject_ = 0;
1660  isTransient_ = false;
1661  }
1662 
1663  while ((numPoints < (1.2*size_)) && (tia_params.relErrorTol >= 1e-6))
1664  {
1665  {
1666  Report::UserWarning() << "Tolerance parameters refined, re-running with relErrorTol = " << tia_params.relErrorTol/10;
1667  }
1668 
1669  if (!startUpPeriodsGiven_)
1670  {
1671  // Clear the fast time data storage before performing the next transient
1673  }
1674 
1675  tia_params.relErrorTol = tia_params.relErrorTol/10;
1676 
1677  // Create a transient analysis object for this section.
1678  {
1679  Xyce::IO::ActiveOutput x(analysisManager_.getOutputManagerAdapter().getOutputManager());
1680  if (!startUpPeriodsGiven_) {
1681  x.add(Xyce::IO::PrintType::HB_IC, ANP_MODE_HB);
1682  x.resetIndex();
1683  }
1684 
1685  isTransient_ = true;
1687  currentAnalysisObject_ = &transient;
1688  analysisManager_.pushActiveAnalysis(&transient);
1690  transient.setTIAParams(tia_params);
1691  transient.setAnalysisParams(Util::OptionBlock());
1692  transient.resetForHB();
1693  nonlinearManager_.resetAll(Nonlinear::DC_OP);
1694  analysisManager_.getStepErrorControl().resetAll(tia_params);
1695  analysisManager_.getDataStore()->resetAll(tia_params.absErrorTol, tia_params.relErrorTol);
1696  analysisManager_.setNextOutputTime(0.0);
1697 
1698  {
1699  if (!transient.run())
1700  {
1701  Report::UserError() << "Calculation of tolerance parameters failed for relErrorTol = " << tia_params.relErrorTol;
1702  return false;
1703  }
1704  }
1705 
1706  numPoints = transient.getStepNumber();
1707 
1708  // Add in simulation times
1709  accumulateStatistics_(transient);
1710 
1711  analysisManager_.popActiveAnalysis();
1712  currentAnalysisObject_ = 0;
1713  isTransient_ = false;
1714  }
1715  }
1716 
1717  return true;
1718 }
1719 
1720 //-----------------------------------------------------------------------------
1721 // Function : HB::runStartupPeriods_()
1722 // Purpose : Runs normal transient problem through the requested
1723 // number of startup periods
1724 // Special Notes :
1725 // Scope : private
1726 // Creator : Richard Schiek, 1437, Electrical and Micro Modeling
1727 // Creation Date : 09/17/07
1728 //-----------------------------------------------------------------------------
1729 bool
1731  const TimeIntg::TIAParams & tia_params)
1732 {
1733  bool returnValue = true;
1734 
1735  Xyce::lout() << " ***** Computing " << startUpPeriods_ << " start up periods for HB IC calculation...." << std::endl;
1736 
1737  if (DEBUG_HB)
1738  Xyce::dout() << "HB::runStartupPeriods_(): Advancing time through "
1739  << startUpPeriods_ << " startup periods"
1740  << " initialTime = " << tia_params.initialTime
1741  << " finalTime = " << tia_params.finalTime << std::endl;
1742 
1743 
1744  // << "HB::runStartupPeriods_(): Double DCOP tia_params:"
1745  // << " doubleDCOPStep = " << tia_params.doubleDCOPStep
1746  // << " firstDCOPStep = " << tia_params.firstDCOPStep
1747  // << " lastDCOPStep = " << tia_params.lastDCOPStep << std::endl
1748 
1749  // << "HB::runStartupPeriods_(): Double DCOP tiaParamsSave:"
1750  // << " doubleDCOPStep = " << tiaParamsSave.doubleDCOPStep
1751  // << " firstDCOPStep = " << tiaParamsSave.firstDCOPStep
1752  // << " lastDCOPStep = " << tiaParamsSave.lastDCOPStep << std::endl;
1753 
1754  {
1755  Xyce::IO::ActiveOutput x(analysisManager_.getOutputManagerAdapter().getOutputManager());
1756  x.add(Xyce::IO::PrintType::HB_STARTUP, ANP_MODE_HB);
1757 
1758  // Create a transient analysis object for this section.
1759  {
1760  isTransient_ = true;
1762  analysisManager_.pushActiveAnalysis(&transient);
1763  currentAnalysisObject_ = &transient;
1764  transient.setTIAParams(tia_params);
1765  transient.setAnalysisParams(Util::OptionBlock());
1766  transient.resetForHB();
1767  nonlinearManager_.resetAll(Nonlinear::DC_OP);
1768  analysisManager_.getStepErrorControl().resetAll(tia_params);
1769  analysisManager_.getDataStore()->resetAll(tia_params.absErrorTol, tia_params.relErrorTol);
1770  analysisManager_.setNextOutputTime(0.0);
1771 
1772  {
1773  returnValue = transient.run();
1774  }
1775 
1776  isTransient_ = false;
1777 
1778  // Add in simulation times
1779  accumulateStatistics_(transient);
1780 
1781  analysisManager_.getOutputManagerAdapter().finishOutput();
1782 
1783  analysisManager_.popActiveAnalysis();
1785  }
1786  }
1787 
1788  // reset the output filename suffix
1789  // analysisManager_.outMgrPtr->setOutputFilenameSuffix("");
1790 
1791  // put the dsPtr->currentSolutionPtr into dcOpSol and State Vec so that it
1792  // is used as our initial condition for the pending fast time scale runs
1794  dcOpSolVecPtr_ = rcp( new Linear::Vector( *(dsPtr->currSolutionPtr) ));
1795  dcOpStateVecPtr_ = rcp( new Linear::Vector( *(dsPtr->currStatePtr) ));
1796  dcOpQVecPtr_ = rcp( new Linear::Vector( *(dsPtr->daeQVectorPtr) ));
1797  dcOpStoreVecPtr_ = rcp( new Linear::Vector( *(dsPtr->currStorePtr) ));
1798 
1799  return returnValue;
1800 }
1801 
1802 //-----------------------------------------------------------------------------
1803 // Function : HB::runTransientIC_
1804 // Purpose : Conducts a regular transient run for HB initial conditions
1805 // Special Notes :
1806 // Scope : private
1807 // Creator : Ting Mei, SNL
1808 // Creation Date : 10/03/2008
1809 //-----------------------------------------------------------------------------
1810 bool
1812  const TimeIntg::TIAParams & tia_params)
1813 {
1814  bool returnValue = true;
1815 
1816  Xyce::lout() << " ***** Running transient to compute HB initial condition....\n" << std::endl;
1817 
1818  // this prevents extra DC op data from being printed.
1819  deviceManager_.setMPDEFlag( true );
1820 
1821  if (DEBUG_HB)
1822  Xyce::dout() << "HB::runTransientIC_(): Advancing time from"
1823  << " initialTime = " << tia_params.initialTime
1824  << " finalTime = " << tia_params.finalTime << std::endl;
1825 
1826  // Initial conditions will be set if startup periods were run.
1828  *(dsPtr->nextSolutionPtr) = *(dcOpSolVecPtr_.get());
1829  *(dsPtr->nextStatePtr) = *(dcOpStateVecPtr_.get());
1830  *(dsPtr->daeQVectorPtr) = *(dcOpQVecPtr_.get());
1831  *(dsPtr->nextStorePtr) = *(dcOpStoreVecPtr_.get());
1832 
1833  // Create a transient analysis object for this section.
1834  {
1835  Xyce::IO::ActiveOutput x(analysisManager_.getOutputManagerAdapter().getOutputManager());
1837  x.add(Xyce::IO::PrintType::HB_IC, ANP_MODE_HB);
1838 
1839  isTransient_ = true;
1841  transient.setNOOP(true);
1842  transient.setSaveTimeSteps(true);
1843  currentAnalysisObject_ = &transient;
1844  analysisManager_.pushActiveAnalysis(&transient);
1845  transient.setTIAParams(tia_params);
1846  transient.setAnalysisParams(Util::OptionBlock());
1847  transient.resetForHB();
1848  nonlinearManager_.resetAll(Nonlinear::DC_OP);
1849  analysisManager_.getStepErrorControl().resetAll(tia_params);
1850  analysisManager_.getDataStore()->resetAll(tia_params.absErrorTol, tia_params.relErrorTol);
1851  analysisManager_.setNextOutputTime(0.0);
1852 
1853  {
1854  returnValue = transient.run();
1855  }
1856 
1857  isTransient_ = false;
1858 
1859  // Add in simulation times
1860  accumulateStatistics_(transient);
1861 
1862  analysisManager_.popActiveAnalysis();
1864  }
1865 
1866  return returnValue;
1867 }
1868 
1869 //-----------------------------------------------------------------------------
1870 // Function : HB::interpolateIC()
1871 // Purpose : Tries to filter the fast time points from a transient run
1872 // so that points are not too close together
1873 // Special Notes :
1874 // Scope : private
1875 // Creator : Richard Schiek, 1437, Electrical and Micro Modeling
1876 // Creation Date : 09/17/07
1877 //-----------------------------------------------------------------------------
1878 bool
1880  double initial_time)
1881 {
1882  Xyce::lout() << " ***** Interpolating transient solution for IC calculation....\n" << std::endl;
1883 
1885  int numPoints = dsPtr->timeSteps.size();
1886 
1887  if (DEBUG_HB)
1888  Xyce::dout() << "HB::interpolateIC_(): Initial transient run produced " << numPoints << " points." << std::endl;
1889 
1890  std::vector<int> goodIndicies;
1891  for( int i = 0; i < size_; ++i )
1892  {
1893  goodTimePoints_[i] = initial_time + goodTimePoints_[i];
1894  }
1895 
1896  bool sortedTimesFlag = true;
1897 
1898  if (freqs_.size() > 1)
1899  sortedTimesFlag = false;
1900 
1901  int breakpoints = 0; // need to keep track of how many breakpoints there are
1902  int startIndex = 0;
1903 
1904  if (sortedTimesFlag)
1905  {
1906  goodIndicies.push_back(startIndex);
1907  int GoodTimePointIndex = startIndex + 1;
1908 
1909  for( int i=startIndex; i < numPoints - 1 ; i++ )
1910  {
1911  // count up breakpoints
1912 
1913  if( dsPtr->timeStepsBreakpointFlag[i] == true )
1914  {
1915  breakpoints++;
1916  }
1917 
1918  if (DEBUG_HB && isActive(Diag::HB_TIMESTEP))
1919  {
1920  Xyce::dout() << "\t\t timeStep[ " << i << " ] = " << dsPtr->timeSteps[i];
1921  if( dsPtr->timeStepsBreakpointFlag[i] == true )
1922  {
1923  Xyce::dout() << " Breakpoint";
1924  }
1925  Xyce::dout() << std::endl;
1926  }
1927 
1928  while( ( GoodTimePointIndex < size_ ) && (dsPtr->timeSteps[i] <= goodTimePoints_[GoodTimePointIndex]) && (goodTimePoints_[GoodTimePointIndex] < dsPtr->timeSteps[i+1]))
1929  {
1930  // found a good point so save the index
1931  goodIndicies.push_back( i );
1932  GoodTimePointIndex = GoodTimePointIndex+1;
1933  }
1934  }
1935  }
1936  else
1937  {
1938  double tmpTimePoints;
1939  bool found;
1940  for(int i=0; i<size_; i++ )
1941  {
1942  tmpTimePoints = fmod(fastTimes_[i], 1.0/freqs_[0]) + initial_time;
1943 
1944  goodTimePoints_[i] = tmpTimePoints;
1945  found = false;
1946 
1947  for(int j=0; (j< (numPoints - 1) && !found ); j++)
1948  {
1949  if((dsPtr->timeSteps[j] <= tmpTimePoints ) && ( tmpTimePoints < dsPtr->timeSteps[j+1]))
1950  {
1951  // found a good point so save the index
1952  goodIndicies.push_back( j );
1953  found=true;
1954  }
1955  }
1956  }
1957  }
1958 
1959  for(int i=0; i<size_; i++ )
1960  {
1961  int currentIndex = goodIndicies[i];
1962  Linear::Vector * firstSolVecPtr = dsPtr->fastTimeSolutionVec[currentIndex];
1963  Linear::Vector * secondSolVecPtr = dsPtr->fastTimeSolutionVec[currentIndex+1];
1964 
1965  Linear::Vector * firstStateVecPtr = dsPtr->fastTimeStateVec[currentIndex];
1966  Linear::Vector * secondStateVecPtr = dsPtr->fastTimeStateVec[currentIndex+1];
1967 
1968  Linear::Vector * firstQVecPtr = dsPtr->fastTimeQVec[currentIndex];
1969  Linear::Vector * secondQVecPtr = dsPtr->fastTimeQVec[currentIndex+1];
1970 
1971  Linear::Vector * firstStoreVecPtr = dsPtr->fastTimeStoreVec[currentIndex];
1972  Linear::Vector * secondStoreVecPtr = dsPtr->fastTimeStoreVec[currentIndex+1];
1973 
1974  double fraction = (goodTimePoints_[i] - dsPtr->timeSteps[currentIndex])/(dsPtr->timeSteps[currentIndex+1] - dsPtr->timeSteps[currentIndex]);
1975 
1976  RCP<Linear::Vector> InterpICSolVecPtr = rcp( new Linear::Vector( *secondSolVecPtr ) );
1977  RCP<Linear::Vector> InterpICStateVecPtr = rcp( new Linear::Vector( *secondStateVecPtr ) );
1978  RCP<Linear::Vector> InterpICQVecPtr = rcp( new Linear::Vector( *secondQVecPtr ) );
1979  RCP<Linear::Vector> InterpICStoreVecPtr = rcp( new Linear::Vector( *secondStoreVecPtr ) );
1980 
1981  InterpICSolVecPtr->putScalar(0.0);
1982  InterpICStateVecPtr->putScalar(0.0);
1983  InterpICQVecPtr->putScalar(0.0);
1984  InterpICStoreVecPtr->putScalar(0.0);
1985 
1986  InterpICSolVecPtr->linearCombo(-1.0, *firstSolVecPtr, 1.0, *secondSolVecPtr );
1987  InterpICSolVecPtr->linearCombo(1.0, *firstSolVecPtr, fraction , *InterpICSolVecPtr);
1988 
1989  InterpICStateVecPtr->linearCombo(-1.0, *firstStateVecPtr, 1.0, *secondStateVecPtr );
1990  InterpICStateVecPtr->linearCombo(1.0, *firstStateVecPtr, fraction , *InterpICStateVecPtr);
1991 
1992  InterpICQVecPtr->linearCombo(-1.0, *firstQVecPtr, 1.0, *secondQVecPtr );
1993  InterpICQVecPtr->linearCombo(1.0, *firstQVecPtr, fraction , *InterpICQVecPtr);
1994 
1995  InterpICStoreVecPtr->linearCombo(-1.0, *firstStoreVecPtr, 1.0, *secondStoreVecPtr );
1996  InterpICStoreVecPtr->linearCombo(1.0, *firstStoreVecPtr, fraction , *InterpICStoreVecPtr);
1997 
1998  goodSolutionVec_.push_back(InterpICSolVecPtr);
1999  goodStateVec_.push_back(InterpICStateVecPtr);
2000  goodQVec_.push_back(InterpICQVecPtr);
2001  goodStoreVec_.push_back(InterpICStoreVecPtr);
2002  }
2003 
2004  // Clean up the fast time data since we are finished computing the initial condition.
2005  // The fast time data can take a considerable amount of memory for large problems.
2006  dsPtr->resetFastTimeData();
2007 
2008  return true;
2009 }
2010 
2011 namespace {
2012 
2013 typedef Util::Factory<AnalysisBase, HB> HBFactoryBase;
2014 
2015 
2016 //-----------------------------------------------------------------------------
2017 // Class : HBFactory
2018 // Purpose :
2019 // Special Notes :
2020 // Scope : public
2021 // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2022 // Creation Date : Thu Jan 29 12:53:02 2015
2023 //-----------------------------------------------------------------------------
2024 ///
2025 /// Factory for parsing HB parameters from the netlist and creating HB analysis.
2026 ///
2027 class HBFactory : public HBFactoryBase
2028 {
2029 public:
2030  //-----------------------------------------------------------------------------
2031  // Function : HBFactory
2032  // Purpose :
2033  // Special Notes :
2034  // Scope : public
2035  // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2036  // Creation Date : Thu Jan 29 12:54:09 2015
2037  //-----------------------------------------------------------------------------
2038  ///
2039  /// Constructs the HB analysis factory
2040  ///
2041  /// @invariant Stores the results of parsing, so if more than one of the analysis and
2042  /// associated lines are parsed, the second options simply overwrite the previously parsed
2043  /// values.
2044  ///
2045  /// @invariant The existence of the parameters specified in the constructor cannot
2046  /// change.
2047  ///
2048  /// @param analysis_manager
2049  /// @param linear_system
2050  /// @param nonlinear_manager
2051  /// @param device_manager
2052  /// @param builder
2053  /// @param topology
2054  ///
2055  HBFactory(
2056  Analysis::AnalysisManager & analysis_manager,
2057  Linear::System & linear_system,
2058  Nonlinear::Manager & nonlinear_manager,
2059  Loader::Loader & loader,
2060  Device::DeviceMgr & device_manager,
2061  Linear::Builder & builder,
2062  Topo::Topology & topology,
2063  IO::InitialConditionsManager & initial_conditions_manager,
2064  IO::RestartMgr & restart_manager)
2065  : HBFactoryBase(),
2066  analysisManager_(analysis_manager),
2067  linearSystem_(linear_system),
2068  nonlinearManager_(nonlinear_manager),
2069  loader_(loader),
2070  deviceManager_(device_manager),
2071  builder_(builder),
2072  topology_(topology),
2073  initialConditionsManager_(initial_conditions_manager),
2074  restartManager_(restart_manager)
2075  {}
2076 
2077  virtual ~HBFactory()
2078  {}
2079 
2080  //-----------------------------------------------------------------------------
2081  // Function : create
2082  // Purpose :
2083  // Special Notes :
2084  // Scope : public
2085  // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2086  // Creation Date : Thu Jan 29 12:59:00 2015
2087  //-----------------------------------------------------------------------------
2088  ///
2089  /// Create a new HB analysis and applies the analysis and time integrator option blocks.
2090  ///
2091  /// @return new HB analysis object
2092  ///
2093  HB *create() const
2094  {
2095  analysisManager_.setAnalysisMode(ANP_MODE_HB);
2096 
2098  hb->setAnalysisParams(hbAnalysisOptionBlock_);
2099  hb->setHBIntParams(hbIntOptionBlock_);
2100  hb->setHBLinSol(hbLinSolOptionBlock_, builder_);
2101  hb->setLinSol(linSolOptionBlock_);
2102 
2103  return hb;
2104  }
2105 
2106  //-----------------------------------------------------------------------------
2107  // Function : setHBAnalysisOptionBlock
2108  // Purpose :
2109  // Special Notes :
2110  // Scope : public
2111  // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2112  // Creation Date : Thu Jan 29 13:00:14 2015
2113  //-----------------------------------------------------------------------------
2114  ///
2115  /// Saves the analysis parsed options block in the factory.
2116  ///
2117  /// @invariant Overwrites any previously specified analysis option block.
2118  ///
2119  /// @param option_block parsed option block
2120  ///
2121  bool setHBAnalysisOptionBlock(const Util::OptionBlock &option_block)
2122  {
2123  hbAnalysisOptionBlock_ = option_block;
2124 
2125  return true;
2126  }
2127 
2128  //-----------------------------------------------------------------------------
2129  // Function : setHBIntOptionBlock
2130  // Purpose :
2131  // Special Notes :
2132  // Scope : public
2133  // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2134  // Creation Date : Thu Jan 29 13:00:14 2015
2135  //-----------------------------------------------------------------------------
2136  ///
2137  /// Saves the HBINT parsed options block in the factory.
2138  ///
2139  /// @invariant Overwrites any previously specified HBINT option block.
2140  ///
2141  /// @param option_block parsed option block
2142  ///
2143  bool setHBIntOptionBlock(const Util::OptionBlock &option_block)
2144  {
2145  hbIntOptionBlock_ = option_block;
2146 
2147  return true;
2148  }
2149 
2150  //-----------------------------------------------------------------------------
2151  // Function : setHBIntOptionBlock
2152  // Purpose :
2153  // Special Notes :
2154  // Scope : public
2155  // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2156  // Creation Date : Thu Jan 29 13:00:14 2015
2157  //-----------------------------------------------------------------------------
2158  ///
2159  /// Saves the LINSOL-HB parsed options block in the factory.
2160  ///
2161  /// @invariant Overwrites any previously specified LINSOL-HB option block.
2162  ///
2163  /// @param option_block parsed option block
2164  ///
2165  bool setHBLinSolOptionBlock(const Util::OptionBlock &option_block)
2166  {
2167  hbLinSolOptionBlock_ = option_block;
2168 
2169  return true;
2170  }
2171 
2172  //-----------------------------------------------------------------------------
2173  // Function : setLinSolOptionBlock
2174  // Purpose :
2175  // Special Notes :
2176  // Scope : public
2177  // Creator : David G. Baur Raytheon Sandia National Laboratories 1355
2178  // Creation Date : Thu Jan 29 13:00:14 2015
2179  //-----------------------------------------------------------------------------
2180  ///
2181  /// Saves the LINSOL parsed options block in the factory.
2182  ///
2183  /// @invariant Overwrites any previously specified LINSOL option block.
2184  ///
2185  /// @param option_block parsed option block
2186  ///
2187  bool setLinSolOptionBlock(const Util::OptionBlock &option_block)
2188  {
2189  linSolOptionBlock_ = option_block;
2190 
2191  return true;
2192  }
2193 
2194 public:
2195  AnalysisManager & analysisManager_;
2196  Linear::System & linearSystem_;
2197  Nonlinear::Manager & nonlinearManager_;
2198  Loader::Loader & loader_;
2199  Device::DeviceMgr & deviceManager_;
2200  Linear::Builder & builder_;
2201  Topo::Topology & topology_;
2202  IO::InitialConditionsManager & initialConditionsManager_;
2203  IO::RestartMgr & restartManager_;
2204 
2205 private:
2206  Util::OptionBlock hbAnalysisOptionBlock_;
2207  Util::OptionBlock timeIntegratorOptionBlock_;
2208  Util::OptionBlock hbIntOptionBlock_;
2209  Util::OptionBlock hbLinSolOptionBlock_;
2210  Util::OptionBlock linSolOptionBlock_;
2211 };
2212 
2213 // .HB
2214 struct HBAnalysisReg : public IO::PkgOptionsReg
2215 {
2216  HBAnalysisReg(
2217  HBFactory & factory )
2218  : factory_(factory)
2219  {}
2220 
2221  bool operator()(const Util::OptionBlock &option_block)
2222  {
2223  factory_.setHBAnalysisOptionBlock(option_block);
2224  factory_.deviceManager_.setBlockAnalysisFlag(true);
2225 
2226  factory_.analysisManager_.addAnalysis(&factory_);
2227 
2228  return true;
2229  }
2230 
2231  HBFactory & factory_;
2232 };
2233 
2234 //-----------------------------------------------------------------------------
2235 // Function : extractHBData
2236 // Purpose : Extract the parameters from a netlist .DC line held in
2237 // parsed_line.
2238 // Special Notes :
2239 // Scope : public
2240 // Creator : Todd Coffey, Rich Schiek
2241 // Creation Date : 7/23/08
2242 //-----------------------------------------------------------------------------
2243 bool
2244 extractHBData(
2245  IO::PkgOptionsMgr & options_manager,
2246  IO::CircuitBlock & circuit_block,
2247  const std::string & netlist_filename,
2248  const IO::TokenVector & parsed_line)
2249 {
2250  Util::OptionBlock option_block("HB", Util::OptionBlock::NO_EXPRESSIONS, netlist_filename, parsed_line[0].lineNumber_);
2251 
2252  int numFields = parsed_line.size();
2253 
2254  // Check that the minimum required number of fields are on the line.
2255  if ( numFields < 2 )
2256  {
2257  Report::UserError0().at(netlist_filename, parsed_line[0].lineNumber_)
2258  << ".HB line has an unexpected number of fields";
2259  }
2260 
2261  int linePosition = 1; // Start of parameters on .param line.
2262  int endPosition = numFields;
2263 
2264  Util::Param parameter("", "");
2265 
2266 // frequency of oscillation is required
2267  std::vector<double> freqs(numFields - 1);
2268 
2269  int i = 0;
2270  while( linePosition < endPosition )
2271  {
2272  const std::string & value = parsed_line[linePosition].string_;
2273  if (Util::isValue(value))
2274  {
2275  freqs[i] = Util::Value(value);
2276  }
2277  else
2278  {
2279  Report::UserError0().at(netlist_filename, parsed_line[0].lineNumber_)
2280  << "Attempt to assign value for FREQ from " << value;
2281  }
2282  ++linePosition;
2283  ++i;
2284  }
2285 
2286  parameter.setTag( "FREQ" );
2287  parameter.setVal( freqs );
2288  option_block.addParam( parameter );
2289 // ++linePosition;
2290 
2291  circuit_block.addOptions(option_block);
2292 
2293  return true;
2294 }
2295 
2296 void
2297 populateMetadata(
2298  IO::PkgOptionsMgr & options_manager)
2299 {
2300  {
2301  Util::ParamMap &parameters = options_manager.addOptionsMetadataMap("LINSOL-HB");
2302 
2303  parameters.insert(Util::ParamMap::value_type("AZ_max_iter", Util::Param("AZ_max_iter", 500)));
2304  parameters.insert(Util::ParamMap::value_type("AZ_solver", Util::Param("AZ_solver", 1)));
2305  parameters.insert(Util::ParamMap::value_type("AZ_conv", Util::Param("AZ_conv", 0)));
2306  parameters.insert(Util::ParamMap::value_type("AZ_pre_calc", Util::Param("AZ_pre_calc", 1)));
2307  parameters.insert(Util::ParamMap::value_type("AZ_keep_info", Util::Param("AZ_keep_info", 1)));
2308  parameters.insert(Util::ParamMap::value_type("AZ_orthog", Util::Param("AZ_orthog", 1)));
2309  parameters.insert(Util::ParamMap::value_type("AZ_reorder", Util::Param("AZ_reorder", 0)));
2310  parameters.insert(Util::ParamMap::value_type("AZ_scaling", Util::Param("AZ_scaling", 0)));
2311  parameters.insert(Util::ParamMap::value_type("AZ_kspace", Util::Param("AZ_kspace", 500)));
2312  parameters.insert(Util::ParamMap::value_type("AZ_tol", Util::Param("AZ_tol", 1.0E-12)));
2313  parameters.insert(Util::ParamMap::value_type("AZ_output", Util::Param("AZ_output", 0)));
2314  parameters.insert(Util::ParamMap::value_type("AZ_diagnostics", Util::Param("AZ_diagnostics", 0)));
2315  parameters.insert(Util::ParamMap::value_type("TYPE", Util::Param("TYPE", "DEFAULT")));
2316  parameters.insert(Util::ParamMap::value_type("PREC_TYPE", Util::Param("PREC_TYPE", "NONE")));
2317  parameters.insert(Util::ParamMap::value_type("BLOCK_JACOBI_CORRECTED", Util::Param("BLOCK_JACOBI_CORRECTED", false)));
2318  }
2319 
2320  {
2321  Util::ParamMap &parameters = options_manager.addOptionsMetadataMap("HBINT");
2322 
2323  parameters.insert(Util::ParamMap::value_type("TEST", Util::Param("TEST", false)));
2324  parameters.insert(Util::ParamMap::value_type("NUMFREQ", Util::Param("NUMFREQ", "VECTOR")));
2325  parameters.insert(Util::ParamMap::value_type("STARTUPPERIODS", Util::Param("STARTUPPERIODS", 0)));
2326  parameters.insert(Util::ParamMap::value_type("SAVEICDATA", Util::Param("SAVEICDATA", false)));
2327  parameters.insert(Util::ParamMap::value_type("DEBUGLEVEL", Util::Param("DEBUGLEVEL", 0)));
2328  parameters.insert(Util::ParamMap::value_type("TAHB", Util::Param("TAHB", 1)));
2329  parameters.insert(Util::ParamMap::value_type("VOLTLIM", Util::Param("VOLTLIM", 1)));
2330  parameters.insert(Util::ParamMap::value_type("INTMODMAX", Util::Param("INTMODMAX",0)));
2331  parameters.insert(Util::ParamMap::value_type("METHOD", Util::Param("METHOD", "APFT")));
2332  parameters.insert(Util::ParamMap::value_type("NUMTPTS", Util::Param("NUMTPTS", 1)));
2333  }
2334 }
2335 
2336 } // namespace <unnamed>
2337 
2338 
2339 bool
2341  FactoryBlock & factory_block)
2342 {
2343  HBFactory *factory = new HBFactory(factory_block.analysisManager_, factory_block.linearSystem_, factory_block.nonlinearManager_,
2344  factory_block.loader_, factory_block.deviceManager_, factory_block.builder_, factory_block.topology_,
2345  factory_block.initialConditionsManager_, factory_block.restartManager_);
2346 
2347  addAnalysisFactory(factory_block, factory);
2348 
2349  populateMetadata(factory_block.optionsManager_);
2350 
2351  factory_block.optionsManager_.addCommandParser(".HB", extractHBData);
2352 
2353  factory_block.optionsManager_.addCommandProcessor("HB", new HBAnalysisReg(*factory));
2354 
2355  factory_block.optionsManager_.addOptionsProcessor("HBINT", IO::createRegistrationOptions(*factory, &HBFactory::setHBIntOptionBlock));
2356  factory_block.optionsManager_.addOptionsProcessor("LINSOL-HB", IO::createRegistrationOptions(*factory, &HBFactory::setHBLinSolOptionBlock));
2357  factory_block.optionsManager_.addOptionsProcessor("LINSOL", IO::createRegistrationOptions(*factory, &HBFactory::setLinSolOptionBlock));
2358 
2359  return true;
2360 }
2361 
2362 } // namespace Analysis
2363 } // namespace Xyce
void accumulateStatistics_(AnalysisBase &analysis)
Definition: N_ANP_HB.C:1098
std::vector< Linear::Vector * > fastTimeQVec
Util::OptionBlock saved_lsHBOB_
Definition: N_ANP_HB.h:245
Linear::HBPrecondFactory * precFactory_
Definition: N_ANP_HB.h:249
bool processFailedDCOP()
Definition: N_ANP_HB.C:595
std::vector< double > timeSteps
Util::OptionBlock linSolOptionBlock_
Definition: N_ANP_HB.C:2210
AnalysisBase * currentAnalysisObject_
Definition: N_ANP_HB.h:188
Teuchos::RCP< Linear::BlockVector > HBICQVectorPtr_
HB initial Q condition.
Definition: N_ANP_HB.h:267
IO::RestartMgr & restartManager_
Definition: N_ANP_HB.C:2203
Teuchos::RCP< N_MPDE_Discretization > mpdeDiscPtr_
Definition: N_ANP_HB.h:238
Loader::Loader & loader_
Definition: N_ANP_HB.C:2198
Linear::Builder & builder_
Definition: N_ANP_HB.h:183
Teuchos::SerialDenseMatrix< int, double > dftMatrix_
Definition: N_ANP_HB.h:242
Loader::Loader & loader_
Definition: N_ANP_HB.h:179
std::vector< double > freqs_
Problem Size.
Definition: N_ANP_HB.h:204
std::vector< bool > timeStepsBreakpointFlag
Teuchos::RCP< Linear::Vector > dcOpStateVecPtr_
Definition: N_ANP_HB.h:253
HBFactory & factory_
Definition: N_ANP_HB.C:2231
std::vector< int > numFreqs_
Definition: N_ANP_HB.h:208
void setNextOutputTime(double next_output_time)
bool printLoopInfo(int start, int finish)
bool startUpPeriodsGiven_
Definition: N_ANP_HB.h:215
IO::InitialConditionsManager & initialConditionsManager_
Definition: N_ANP_HB.h:185
Pure virtual class to augment a linear system.
void registerDFTInterface(const Teuchos::RCP< N_UTL_DFTInterfaceDecl< std::vector< double > > > &dftInterface)
std::vector< double > freqPoints_
Definition: N_ANP_HB.h:237
bool test_
Testing Flag.
Definition: N_ANP_HB.h:200
void setFastTimes(const std::vector< double > &times)
void setTIAParams(const TimeIntg::TIAParams &tia_params)
void pushActiveAnalysis(AnalysisBase *analysis)
bool isTransient_
Current analysis state flags.
Definition: N_ANP_HB.h:198
bool setAnalysisParams(const Util::OptionBlock &option_block)
Definition: N_ANP_HB.C:642
Linear::System & linearSystem_
Definition: N_ANP_HB.C:2196
std::string method_
Definition: N_ANP_HB.h:226
Linear::Vector * currStorePtr
std::vector< double > iftOutData_
Definition: N_ANP_HB.h:231
Teuchos::RCP< Linear::Vector > dcOpSolVecPtr_
Definition: N_ANP_HB.h:252
void permutedIFT(const Linear::BlockVector &xf, Linear::BlockVector *xt, int numTimePts_=0)
bool isAnalysis(int analysis_type) const
Definition: N_ANP_HB.C:812
Topo::Topology & topology_
Definition: N_ANP_HB.C:2201
double finalTime
End time for simulation.
std::vector< double > timeSteps_
Definition: N_ANP_HB.h:236
AnalysisManager & analysisManager_
Definition: N_ANP_HB.h:178
Util::OptionBlock hbIntOptionBlock_
Definition: N_ANP_HB.C:2208
virtual int getDoubleDCOPStep() const
std::vector< double > ftInData_
Definition: N_ANP_HB.h:231
std::vector< Linear::Vector * > fastTimeStateVec
Teuchos::SerialDenseMatrix< int, double > idftMatrix_
Definition: N_ANP_HB.h:242
N_PDS_Manager * pdsMgrPtr_
Definition: N_ANP_HB.h:187
Util::ListenerAutoSubscribe< StepEvent > StepEventListener
std::vector< double > ftOutData_
Definition: N_ANP_HB.h:231
void setAnalysisMode(AnalysisMode mode)
const T & value(const ParameterBase &entity, const Descriptor &descriptor)
Returns the value of the parameter for the entity.
Definition: N_DEV_Pars.h:1224
Linear::Vector * currStatePtr
Teuchos::RCP< Linear::HBBuilder > hbBuilderPtr_
HB loader, builder, system, and DFT.
Definition: N_ANP_HB.h:190
Parallel::Manager * getPDSManager() const
bool updateIFT_(std::vector< double > &tPoints)
Definition: N_ANP_HB.C:1581
TimeIntg::StepErrorControl & getStepErrorControl()
Device::DeviceMgr & deviceManager_
Definition: N_ANP_HB.h:182
std::vector< Linear::Vector * > fastTimeSolutionVec
std::vector< Teuchos::RCP< Linear::Vector > > goodStateVec_
Definition: N_ANP_HB.h:259
void permutedFFT(const Linear::BlockVector &xt, Linear::BlockVector *xf)
bool doLoopProcess()
Definition: N_ANP_HB.C:500
Linear::System * hbLinearSystem_
Definition: N_ANP_HB.h:191
bool interpolateIC(double initial_time)
Definition: N_ANP_HB.C:1879
bool runStartupPeriods(const TimeIntg::TIAParams &tia_params)
Definition: N_ANP_HB.C:1730
bool setLinSol(const Util::OptionBlock &option_block)
Definition: N_ANP_HB.C:775
void setMatrixFreeFlag(bool matrixFreeFlag)
void prepareHBOutput(Linear::Vector &solnVecPtr, std::vector< double > &timePoints, std::vector< double > &freqPoints, Teuchos::RCP< Linear::BlockVector > &timeDomainSolnVec, Teuchos::RCP< Linear::BlockVector > &freqDomainSolnVecReal, Teuchos::RCP< Linear::BlockVector > &freqDomainSolnVecImaginary, Teuchos::RCP< Linear::BlockVector > &timeDomainStoreVec, Teuchos::RCP< Linear::BlockVector > &freqDomainStoreVecReal, Teuchos::RCP< Linear::BlockVector > &freqDomainStoreVecImaginary, Teuchos::RCP< Linear::BlockVector > &timeDomainLeadCurrentVec, Teuchos::RCP< Linear::BlockVector > &freqDomainLeadCurrentVecReal, Teuchos::RCP< Linear::BlockVector > &freqDomainLeadCurrentVecImaginary, Teuchos::RCP< Linear::BlockVector > &timeDomainJunctionVoltageVec, Teuchos::RCP< Linear::BlockVector > &freqDomainJunctionVoltageVecReal, Teuchos::RCP< Linear::BlockVector > &freqDomainJunctionVoltageVecImaginary)
Definition: N_ANP_HB.C:825
std::vector< Teuchos::RCP< Linear::Vector > > goodStoreVec_
Definition: N_ANP_HB.h:261
Linear::Vector * daeQVectorPtr
Teuchos::RCP< Linear::Vector > dcOpStoreVecPtr_
Definition: N_ANP_HB.h:255
Device::DeviceMgr & deviceManager_
Definition: N_ANP_HB.C:2199
Teuchos::RCP< Linear::BlockVector > HBICVectorPtr_
Definition: N_ANP_HB.h:264
bool setLinSolOptions(const Util::OptionBlock &option_block)
void resetAll(AnalysisMode mode)
Linear::Vector * deviceErrorWeightMask_
void setSaveTimeSteps(bool save_time_steps)
IO::InitialConditionsManager & initialConditionsManager_
Definition: N_ANP_HB.C:2202
Teuchos::RCP< Linear::BlockVector > & getLeadCurrentVecFreqPtr()
virtual bool isPDESystem() const
Definition: N_LOA_Loader.h:256
bool initializeSolverSystem(const TimeIntg::TIAParams &tia_params, Loader::Loader &loader, Linear::System &linear_system, Nonlinear::Manager &nonlinear_manager, Device::DeviceMgr &device_manager)
Initializes the solver system.
bool doProcessFailedStep()
Definition: N_ANP_HB.C:582
int getDoubleDCOPStep() const
Definition: N_ANP_HB.C:230
virtual bool getDCOPFlag() const =0
bool resetForStepCalledBefore_
Definition: N_ANP_HB.h:273
Teuchos::RCP< Linear::BlockVector > HBICStoreVectorPtr_
HB initial store condition.
Definition: N_ANP_HB.h:268
std::vector< int > numPosFreqs
Definition: N_ANP_HB.h:207
void setMPDEFlag(bool flagVal)
The FactoryBlock contains parameters needed by the analysis creation functions.
IO::InitialConditionsManager & initialConditionsManager_
Nonlinear::AnalysisMode nonlinearAnalysisMode(Mode mode)
Returns the nonlinear analysis mode given the analysis mode.
void setHBFreqs(const std::vector< double > &freqs)
Teuchos::RCP< N_UTL_DFTInterfaceDecl< std::vector< double > > > dftInterface_
Definition: N_ANP_HB.h:241
int startUpPeriods_
Periodicity Information.
Definition: N_ANP_HB.h:214
void registerHBBuilder(Teuchos::RCP< Linear::HBBuilder > hbBuilderPtr)
bool runTol(TimeIntg::TIAParams &tia_params)
Definition: N_ANP_HB.C:1620
N_MPDE_Discretization::Type fastTimeDisc_
Definition: N_ANP_HB.h:233
Teuchos::RCP< Linear::Vector > dcOpQVecPtr_
Definition: N_ANP_HB.h:254
Teuchos::RCP< Linear::BlockVector > HBICVectorFreqPtr_
Definition: N_ANP_HB.h:265
OutputMgrAdapter & getOutputManagerAdapter() const
Linear::Vector * nextStatePtr
std::vector< Linear::Vector * > fastTimeStoreVec
bool initializeAll(Linear::System &linear_system)
Loader::NonlinearEquationLoader & getNonlinearEquationLoader()
Util::OptionBlock saved_lsOB_
Definition: N_ANP_HB.h:246
bool initializeAll(Analysis::AnalysisManager &analysis_manager, Loader::NonlinearEquationLoader &nonlinear_equation_loader, Linear::System &linear_system, TimeIntg::DataStore &data_store, Parallel::Manager &parallel_manager, IO::InitialConditionsManager &initial_conditions_manager, IO::OutputMgr &output_manager, Topo::Topology &topology)
virtual ~HB()
Definition: N_ANP_HB.C:159
bool setFreqPoints_()
Definition: N_ANP_HB.C:1111
double pauseTime
Time step value at which to "pause" the simulation.
void setDoubleDCOPEnabled(bool enable)
bool setInitialGuess()
Definition: N_ANP_HB.C:1515
Teuchos::RCP< Linear::BlockVector > & getStoreVecFreqPtr()
std::vector< double > iftInData_
Definition: N_ANP_HB.h:231
Nonlinear::Manager & nonlinearManager_
Nonlinear::Manager & nonlinearManager_
Definition: N_ANP_HB.C:2197
bool getDCOPFlag() const
Definition: N_ANP_HB.C:246
Loader::HBLoader * hbLoaderPtr_
Definition: N_ANP_HB.h:189
Linear::Vector * nextSolutionPtr
void deRegisterFastSources(const std::vector< std::string > &sourceNames)
Linear::Builder & builder_
Definition: N_ANP_HB.C:2200
Topo::Topology & topology_
Definition: N_ANP_HB.h:184
#define M_PI
Linear::Vector * nextStorePtr
void addAnalysisFactory(FactoryBlock &factory_block, Util::Factory< AnalysisBase, void > *factory)
double initialTime
Beginning time for the time integrator (StepErrorControl, integrators access from StepErrorControl) ...
HB(AnalysisManager &analysis_manager, Linear::System &linear_system, Nonlinear::Manager &nonlinear_manager, Loader::Loader &loader, Device::DeviceMgr &device_manager, Linear::Builder &builder, Topo::Topology &topology, IO::InitialConditionsManager &initial_conditions_manager, IO::RestartMgr &restart_manager)
Definition: N_ANP_HB.C:101
StatCounts hbStatCounts_
Definition: N_ANP_HB.h:271
Teuchos::RCP< Linear::BlockVector > HBICStateVectorPtr_
HB initial state condition.
Definition: N_ANP_HB.h:266
std::vector< double > goodTimePoints_
Definition: N_ANP_HB.h:257
bool processSuccessfulDCOP()
Definition: N_ANP_HB.C:556
void setVoltageLimiterFlag(bool flagVal)
Linear::System & linearSystem_
Definition: N_ANP_HB.h:180
std::vector< Teuchos::RCP< Linear::Vector > > goodQVec_
Definition: N_ANP_HB.h:260
IO::RestartMgr & restartManager_
Definition: N_ANP_HB.h:186
bool doProcessSuccessfulStep()
Definition: N_ANP_HB.C:569
bool setHBIntParams(const Util::OptionBlock &option_block)
Definition: N_ANP_HB.C:682
bool runTransientIC(const TimeIntg::TIAParams &tia_params)
Definition: N_ANP_HB.C:1811
Teuchos::RCP< N_UTL_FFTInterface< std::vector< double > > > ftInterface_
Definition: N_ANP_HB.h:230
Linear::Vector * currSolutionPtr
bool setTimePoints_()
Definition: N_ANP_HB.C:1356
TimeIntg::DataStore * getDataStore()
std::vector< Teuchos::RCP< Linear::Vector > > goodSolutionVec_
Definition: N_ANP_HB.h:258
bool setHBLinSol(const Util::OptionBlock &option_block, Linear::Builder &builder)
Definition: N_ANP_HB.C:791
AnalysisManager & analysisManager_
Definition: N_ANP_HB.C:2195
Nonlinear::Manager & nonlinearManager_
Definition: N_ANP_HB.h:181
std::vector< double > registerFastSources(Parallel::Machine comm, const std::vector< std::string > &sourceNames)
void setMatrixFreeFlag(bool matrixFreeFlag)
Util::OptionBlock timeIntegratorOptionBlock_
Definition: N_ANP_HB.C:2207
bool finalVerboseOutput()
Definition: N_ANP_HB.C:628
bool registerPrecondFactory(const Linear::PrecondFactory *preconditioner_factory)
Util::OptionBlock hbLinSolOptionBlock_
Definition: N_ANP_HB.C:2209
void registerAppLoader(Teuchos::RCP< Loader > appLoaderPtr)
Util::OptionBlock hbAnalysisOptionBlock_
Definition: N_ANP_HB.C:2206
bool doHandlePredictor()
Definition: N_ANP_HB.C:615
std::vector< double > fastTimes_
Definition: N_ANP_HB.h:235
void notify(const StepEvent &event)
Definition: N_ANP_HB.C:174
bool registerHBFactory(FactoryBlock &factory_block)
Definition: N_ANP_HB.C:2340
bool loadDeviceErrorWeightMask(Linear::Vector *deviceMask) const