moutil.c 72 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317131813191320132113221323132413251326132713281329133013311332133313341335133613371338133913401341134213431344134513461347134813491350135113521353135413551356135713581359136013611362136313641365136613671368136913701371137213731374137513761377137813791380138113821383138413851386138713881389139013911392139313941395139613971398139914001401140214031404140514061407140814091410141114121413141414151416141714181419142014211422142314241425142614271428142914301431143214331434143514361437143814391440144114421443144414451446144714481449145014511452145314541455145614571458145914601461146214631464146514661467146814691470147114721473147414751476147714781479148014811482148314841485148614871488148914901491149214931494149514961497149814991500150115021503150415051506150715081509151015111512151315141515151615171518151915201521152215231524152515261527152815291530153115321533153415351536153715381539154015411542154315441545154615471548154915501551155215531554155515561557155815591560156115621563156415651566156715681569157015711572157315741575157615771578157915801581158215831584158515861587158815891590159115921593159415951596159715981599160016011602160316041605160616071608160916101611161216131614161516161617161816191620162116221623162416251626
  1. /* Utility definitions for code generated
  2. * from Modelica translator.
  3. *
  4. * Author: Hilding Elmqvist, Dynasim AB
  5. *
  6. * Copyright (C) 1998-2001 Dynasim AB.
  7. * All rights reserved.
  8. *
  9. * Version: 1.0, 1998-08-18
  10. * 1.1, 1998-10-21, handling of states
  11. * 1.2, 1998-10-29, handling of events
  12. * 1.3, 1999-01-13, matrix features
  13. * 1.4, 1999-02-22, support for solving nonlinear equations
  14. */
  15. #if !defined(RT)
  16. #include <assert.h>
  17. #endif
  18. #ifndef DYMOLA_MOUTIL_C
  19. #include <math.h>
  20. #define DYMOLA_MOUTIL_C
  21. #include <math.h>
  22. #if !defined(DYMOLA_DSPACE) && !defined(NO_FILE)
  23. #include "amat.h"
  24. #endif
  25. #if defined(DymolaStoreProtectedVariables_)
  26. static int DYNStoreProtectedVariables=1;
  27. #else
  28. static int DYNStoreProtectedVariables=0;
  29. #endif
  30. #if !defined(DSE_STRUCT)
  31. #if defined(DS_EMBEDDED)
  32. #define DSE_STRUCT sts->
  33. #else
  34. #define DSE_STRUCT
  35. #endif
  36. #endif
  37. #ifndef DYNX
  38. #if _MSC_VER>=1700
  39. #define DYNX(s,i) (*(s+i))
  40. #else
  41. #define DYNX(s,i) s[i]
  42. #endif
  43. #endif
  44. #define Modelica
  45. DYMOLA_STATIC double* delayID;
  46. DYMOLA_STATIC double Buffersize;
  47. #include "dsblock.h"
  48. #ifndef DYNassert_static
  49. #define DYNassert_static(e) do { enum { DYN_assert_static_=1/(e) }; } while(0)
  50. #endif
  51. struct NonAlias_ {int tag;const char*n;const char*d;double val;double mi;double ma;double w;int ix;};
  52. #undef SpuriousEvents_
  53. #define SpuriousEvents_ 0
  54. /* ---------------------------------------------------- */
  55. /* Macros to define variable names. */
  56. #define SParameter(i) ((const char*)(DYNX(cuser_,i)))
  57. #define Parameter(i) DYNX(DP_,i)
  58. #define Variable(i) DYNX(W_,i)
  59. #define State(i) DYNX(X_,i)
  60. #define Derivative(i) DYNX(F_,i)
  61. #define Input(i) DYNX(U_,i)
  62. #define Output(i) DYNX(Y_,i)
  63. #define Aux(i) DYNX(Aux_,i)
  64. #define SAux(i) DYNX(DYNAuxStr_,i+DYNStrInit(did_))
  65. /* ---------------------------------------------------- */
  66. /* Macros for equations */
  67. #define IF (
  68. #define THEN ) ? (
  69. #define ELSE ) :
  70. #define AND &&
  71. #define OR ||
  72. #define NSAND &
  73. #define NSOR |
  74. #define NOT !
  75. #define EventEPS 1E-8
  76. #define Crossing(x, y, nr, op) \
  77. (Qenable_[nr]=true, \
  78. QZ_[2*nr] = (x) - (y) - EventEPS, \
  79. QZ_[2*nr+1] = (x) - (y) + EventEPS
  80. static
  81. #if defined(_MSC_VER) && _MSC_VER>=1200
  82. __inline
  83. #elif __GNUC__
  84. __inline
  85. #endif
  86. double ScaledCross(double x,double y,double nom,double*r) {
  87. double v=x-y;
  88. *r=(x>nom) ? x : (-x>nom)? -x : nom;
  89. return v;
  90. }
  91. #define Greater(x, sx, y, sy, nr) HandleEvent2( (ScaledCross((x),(y),1.0,Qscaled_+nr)),sx,">",sy,(nr+1), 0, 0)
  92. #define Less(x, sx, y, sy, nr) HandleEvent2( (ScaledCross((x),(y),1.0,Qscaled_+nr)) ,sx, "<", sy,(nr+1), 1, 0)
  93. #define GreaterEqual(x,sx,y,sy,nr) HandleEvent2( (ScaledCross((x),(y),1.0,Qscaled_+nr)), sx, ">=", sy,(nr+1), 1, 1)
  94. #define LessEqual(x,sx,y,sy,nr) HandleEvent2( (ScaledCross((x),(y),1.0,Qscaled_+nr)), sx, "<=", sy,(nr+1), 0, 1)
  95. #define GreaterMinor(x, sx, y, sy, nr) HandleEvent2Minor( (ScaledCross((x),(y),1.0,Qscaled_+nr)),sx,">",sy,(nr+1), 0, 0)
  96. #define LessMinor(x, sx, y, sy, nr) HandleEvent2Minor( (ScaledCross((x),(y),1.0,Qscaled_+nr)) ,sx, "<", sy,(nr+1), 1, 0)
  97. #define GreaterEqualMinor(x,sx,y,sy,nr) HandleEvent2Minor( (ScaledCross((x),(y),1.0,Qscaled_+nr)), sx, ">=", sy,(nr+1), 1, 1)
  98. #define LessEqualMinor(x,sx,y,sy,nr) HandleEvent2Minor( (ScaledCross((x),(y),1.0,Qscaled_+nr)), sx, "<=", sy,(nr+1), 0, 1)
  99. #define GreaterS(x, sx, y, sy, nr) HandleEvent2S( (ScaledCross((x),(y),1.0,Qscaled_+nr)) ,sx,">",sy,(nr+1), 0, 0)
  100. #define LessS(x, sx, y, sy, nr) HandleEvent2S( (ScaledCross((x),(y),1.0,Qscaled_+nr)) ,sx, "<", sy,(nr+1), 1, 0)
  101. #define GreaterEqualS(x,sx,y,sy,nr) HandleEvent2S( (ScaledCross((x),(y),1.0,Qscaled_+nr)), sx, ">=", sy,(nr+1), 1, 1)
  102. #define LessEqualS(x,sx,y,sy,nr) HandleEvent2S( (ScaledCross((x),(y),1.0,Qscaled_+nr)), sx, "<=", sy,(nr+1), 0, 1)
  103. #define absEvent(x,sx,nr) (Qscaled_[nr]=1,HandleEvent2((x),sx," > ","0",(nr+1),0,0)?QRel_[nr]:-QRel_[nr])
  104. #define signEvent(x,sx,nr1,nr2) (Qscaled_[nr1]=Qscaled_[nr2]=1,HandleEvent2((x),sx," > ","0",(nr1+1),0,0)?1: \
  105. HandleEvent2(QRel_[nr1],sx," < ","0",(nr2+1),1,0)?-1:0)
  106. #define simplesignEvent(x,sx,nr1) (Qscaled_[nr1]=1,HandleEvent2((x),sx," > ","0",(nr1+1),0,0)?1:-1)
  107. #define Equal(x, y, nr) \
  108. ((x) == (y))
  109. #define NotEqual(x, y, nr) \
  110. ((x) != (y))
  111. #define pre(x, sx, start, nr)\
  112. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;AnyEvent_=true;}\
  113. else if (DYNX(QPre_,nr)!=x && !(!Init_ && DymolaOneIteration_ == 5 && !final_)) {\
  114. AnyEvent_=true;\
  115. if (PrintEvent&(1<<1)) VariableChanged(sx,x,DYNTime);\
  116. if (!Init_ && final_==1 && (DymolaOneIteration_==2 || DymolaOneIteration_==3 || DymolaOneIteration_==5)) ; else DYNX(QPre_,nr)=x;\
  117. }
  118. #define preCont(x, sx, start, nr)\
  119. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;}\
  120. else {\
  121. DYNX(QPre_,nr)=x;\
  122. }
  123. #define preW(x, sx, start, nr)\
  124. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;}\
  125. else if (DYNX(QPre_,nr)!=x && !(!Init_ && DymolaOneIteration_ == 5 && !final_)) {\
  126. if (PrintEvent&(1<<1)) VariableChanged(sx,x,DYNTime);\
  127. if (!Init_ && final_==1 && (DymolaOneIteration_==2 || DymolaOneIteration_==3 || DymolaOneIteration_==5)) ; else DYNX(QPre_,nr)=x;\
  128. }
  129. #define preD(x, sx, start, nr)\
  130. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;AnyEvent_=true;}\
  131. else if (DYNX(QPre_,nr)!=x && !(!Init_ && DymolaOneIteration_ == 5 && !final_)) {\
  132. AnyEvent_=true;\
  133. AnyDEvent_=true;\
  134. if (PrintEvent&(1<<1)) VariableChanged(sx,x,DYNTime);\
  135. if (!Init_ && final_==1 && (DymolaOneIteration_==2 || DymolaOneIteration_==3 || DymolaOneIteration_==5)) ; else DYNX(QPre_,nr)=x;\
  136. }
  137. #define preContD(x, sx, start, nr)\
  138. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;}\
  139. else {\
  140. if (DYNX(QPre_,nr)!=x) AnyDEvent_=true;\
  141. DYNX(QPre_,nr)=x;\
  142. }
  143. #define preWD(x, sx, start, nr)\
  144. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;}\
  145. else if (DYNX(QPre_,nr)!=x && !(!Init_ && DymolaOneIteration_ == 5 && !final_)) {\
  146. AnyDEvent_=true;\
  147. if (PrintEvent&(1<<1)) VariableChanged(sx,x,DYNTime);\
  148. if (!Init_ && final_==1 && (DymolaOneIteration_==2 || DymolaOneIteration_==3 || DymolaOneIteration_==5)) ; else DYNX(QPre_,nr)=x;\
  149. }
  150. #define preI(x, sx, start, nr)\
  151. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;AnyEvent_=true;}\
  152. else if (DYNX(QPre_,nr)!=x && !(!Init_ && DymolaOneIteration_ == 5 && !final_)) {\
  153. AnyEvent_=true;\
  154. AnyIEvent_=true;\
  155. if (PrintEvent&(1<<1)) VariableChanged(sx,x,DYNTime);\
  156. if (!Init_ && final_==1 && (DymolaOneIteration_==2 || DymolaOneIteration_==3 || DymolaOneIteration_==5)) ; else DYNX(QPre_,nr)=x;\
  157. }
  158. #define preContI(x, sx, start, nr)\
  159. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;}\
  160. else {\
  161. if (DYNX(QPre_,nr)!=x) AnyIEvent_=true;\
  162. DYNX(QPre_,nr)=x;\
  163. }
  164. #define preWI(x, sx, start, nr)\
  165. if (Init_ && (DymolaOneIteration_ == 0 || !final_ && DymolaOneIteration_ == 2) ) { DYNX(QPre_,nr)=start;}\
  166. else if (DYNX(QPre_,nr)!=x && !(!Init_ && DymolaOneIteration_ == 5 && !final_)) {\
  167. AnyIEvent_=true;\
  168. if (PrintEvent&(1<<1)) VariableChanged(sx,x,DYNTime);\
  169. if (!Init_ && final_==1 && (DymolaOneIteration_==2 || DymolaOneIteration_==3 || DymolaOneIteration_==5)) ; else DYNX(QPre_,nr)=x;\
  170. }
  171. static double spliceFunction2(double x,double deltax) {
  172. if (deltax<0) {
  173. x=-x;
  174. deltax=-deltax;
  175. }
  176. if (x<=-deltax) {
  177. return 0;
  178. } else if (x>=deltax) {
  179. return 1;
  180. } else {
  181. double piHalf=asin(1.0);
  182. return (1+tanh(tan((x/deltax)*piHalf)))/2;
  183. }
  184. }
  185. static double spliceFunction2der(double x,double deltax,double dx,double ddeltax) {
  186. if (deltax<0) {
  187. x=-x;
  188. deltax=-deltax;
  189. dx=-dx;
  190. ddeltax=-ddeltax;
  191. }
  192. if (x<=-deltax || x>=deltax) {
  193. return 0;
  194. } else {
  195. double piHalf=asin(1.0);
  196. double x1=(x/deltax);
  197. double y=x1*piHalf;
  198. double z=cosh(tan(y))*cos(y);
  199. return ((dx-x1*ddeltax)*(piHalf)/(2*deltax))/(z*z);
  200. }
  201. }
  202. #define spliceFunction(pos, neg, x, deltax, id) \
  203. (((double*)DYNhelp)[id]=spliceFunction2((x),(deltax)), \
  204. ((double*)DYNhelp)[id]*(((double*)DYNhelp)[id]>0 ? (pos) : 0.0)+(1-((double*)DYNhelp)[id])*(((double*)DYNhelp)[id]<1 ? (neg) : 0.0))
  205. #define spliceFunction_der(pos, neg, x, deltax, pos_der, neg_der, x_der, deltax_der, id) \
  206. (((double*)DYNhelp)[id]=spliceFunction2((x),(deltax)), \
  207. ((double*)DYNhelp)[id]*(((double*)DYNhelp)[id]>0 ? (pos_der) : 0.0)+(1-((double*)DYNhelp)[id])*(((double*)DYNhelp)[id]<1 ? (neg_der) : 0.0)\
  208. + (((double*)DYNhelp)[id]>0 && ((double*)DYNhelp)[id]<1 ? spliceFunction2der((x),(deltax),(x_der),(deltax_der))*((pos)-(neg)): 0.0))
  209. #define PRE(x, nr) DYNX(QPre_,nr)
  210. #define Remember_(x, nr) \
  211. x=(solverHandleEq_ && EqRemember1Time_>-1e30 && EqRemember1Time_<EqRemember2Time_) ?\
  212. DYNX(EqRemember1_,nr)+Dymola_min(4,(DYNTime-EqRemember1Time_)/(EqRemember2Time_-EqRemember1Time_))*(DYNX(EqRemember2_,nr)-DYNX(EqRemember1_,nr)):\
  213. DYNX(EqRemember2_,nr)
  214. #define RememberSimple_(x, nr) \
  215. DYNX(EqRemember2_,nr)
  216. #define DoRemember_(x,val,nr) DYNX(EqRemember2_,nr)=(initializationPhase_==1) ? (val) : (x)
  217. #define event(x) \
  218. (x)
  219. #define noEvent(x) \
  220. (x)
  221. #define reinit(x, expr) \
  222. (x = expr, AnyREvent_=1, 0);
  223. #define reinitNew(x, expr, hv, iv) \
  224. (((DymolaOneIteration_==0) ? (x = expr):(hv=expr,iv=1)), AnyREvent_=1, 0);
  225. #define reinitNewArray(x, expr, hv, iv) \
  226. (((DymolaOneIteration_==0) ? (RealAssign(x,expr)):(RealAssign(hv,expr),iv=1)), AnyREvent_=1, 0);
  227. #define delay(expr, DelayTime, MaxDelayTime, nr, str) \
  228. (delayID[nr]= (delayID[nr]==0) ? 1+delayIni(Dymola_abs(DelayTime), Buffersize, DYNTime, expr) : delayID[nr], \
  229. delayFunction(delayID[nr]-1, Dymola_abs(DelayTime), MaxDelayTime, DYNTime, expr, str))
  230. #define delayDC(expr, DelayTime, nr, nrC) \
  231. delayDCFunction(expr, DelayTime, delayID+nr, Buffersize, DYNTime, DYNEvent, QRel_+nrC, Qp_+nrC, Qn_+nrC,\
  232. Qenable_+1+nrC, QZ_+2*nrC,&AnyEvent_)
  233. #define delayDD(expr, DelayTime, nr, nrT) \
  234. delayDDFunction(expr, DelayTime, delayID+nr, Buffersize, DYNTime, DYNEvent, QTimed_+nrT)
  235. /* ---------------------------------------------------- */
  236. #define NonLinearSystemOfEquations(Jac, res, x, n, numericJacobian, nr, base, hv, nhv, iv, niv) \
  237. { \
  238. DeclareDidRealMatrix1(Jac, n, n, hv); \
  239. Real *Jac##__DWork=(&hv)+n*n; \
  240. int Jac##__LDWork=(20+((n+15)*n)/2);\
  241. int *Jac##__IWork=&iv;\
  242. static const int QBase=base;\
  243. struct MyJmpBuf saved_jmp_buf_env; \
  244. DeclareDidRealVector1(res, n, (&hv)[n*n+(20+((n+15)*n)/2)+0*n]); \
  245. DeclareDidRealVector1(x, n, (&hv)[n*n+(20+((n+15)*n)/2)+1*n]); \
  246. DeclareDidRealVector1(xInitial, n, (&hv)[n*n+(20+((n+15)*n)/2)+2*n]); \
  247. DeclareDidRealVector1(xJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+3*n]); \
  248. DeclareDidRealVector1(resJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+4*n]); \
  249. DeclareDidRealVector1(resJac2, n, (&hv)[n*n+(20+((n+15)*n)/2)+5*n]); \
  250. double lambda_=-2;\
  251. int *storedXP_=(&iv)+20+n;\
  252. int firstTime=1;\
  253. int* storedResetCounterP=(&iv)+21+n;\
  254. int veryFirstTime=ResetCounter_!=*(storedResetCounterP);\
  255. int veryFirstTime2=0;\
  256. int changePmatrix_=0;\
  257. int changePmatrixOld_=0;\
  258. int changePloop_=0;\
  259. int QNnl;int Qinfo,QNLnr,QiOpt,QInfRev;\
  260. DeclareDidRealMatrix2(Jac, n, n, hv);\
  261. DeclareDidRealVector2(res, n, (&hv)[n*n+(20+((n+15)*n)/2)+0*n]); \
  262. DeclareDidRealVector2(x, n, (&hv)[n*n+(20+((n+15)*n)/2)+1*n]); \
  263. DeclareDidRealVector2(xInitial, n, (&hv)[n*n+(20+((n+15)*n)/2)+2*n]); \
  264. DeclareDidRealVector2(xJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+3*n]); \
  265. DeclareDidRealVector2(resJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+4*n]); \
  266. DeclareDidRealVector2(resJac2, n, (&hv)[n*n+(20+((n+15)*n)/2)+5*n]); \
  267. DYNassert_static(nhv==n*n+(20+((n+15)*n)/2)+6*n && niv==22+n);\
  268. if (veryFirstTime) {int i;(*storedXP_)=0;for(i=0;i<n;i++) x##__internal[i]=0,res##__internal[i]=0;for(i=0;i<20+n;++i) Jac##__IWork[i]=0;for(i=0;i<20+((n+15)*n)/2;++i) Jac##__DWork[i]=0;}\
  269. again##nr: firstTime=1; againsecond##nr:\
  270. if (DymolaUserHomotopy) {lambda_=1-DymolaHomotopyLambda;if (DymolaHomotopyLambda==0) veryFirstTime=1;}\
  271. veryFirstTime2=(*(storedResetCounterP)==0);\
  272. *(storedResetCounterP)=ResetCounter_;\
  273. saved_jmp_buf_env = DYNGlobal_jmp_buf_env;\
  274. QNnl = n; \
  275. if (DYNEvent || ! DAEsolver_) { \
  276. QNLnr = nr; \
  277. QiOpt = numericJacobian+1; \
  278. QInfRev = -11+(numericJacobian?1:-DymolaNonLinearIterations_); \
  279. if ((!DymolaNewJacobian_ && !veryFirstTime) || !firstTime) QInfRev=-20-DymolaNonLinearIterations_-10*(1-DymolaAllowNewJacobianAnyway_);\
  280. if (inJacobian_ && !(*storedXP_)) {RealAssign(xJac,x); RealAssign(resJac,res); (*storedXP_)=1;\
  281. } else if ((*storedXP_)) {RealAssign(x,xJac);(*storedXP_)=inJacobian_;}\
  282. } else { \
  283. int i_;\
  284. QInfRev = 0;\
  285. for (i_=1; i_<=QNnl; i_++) \
  286. SetVector(x, i_, ((double*)(DSE_STRUCT X_))[i_+QBase]); \
  287. }
  288. #define NonLinearSystemOfEquationsNH(Jac, res, x, n, numericJacobian, nr, base, nin, hv, nhv, iv, niv) \
  289. { \
  290. DeclareDidRealMatrix1(Jac, n, n, hv); \
  291. Real *Jac##__DWork=(&hv)+n*n; \
  292. int Jac##__LDWork=(20+((n+15)*n)/2);\
  293. int *Jac##__IWork=&iv;\
  294. static const int QBase=base;\
  295. struct MyJmpBuf saved_jmp_buf_env; \
  296. DeclareDidRealVector1(res, n, (&hv)[n*n+(20+((n+15)*n)/2)+0*n]); \
  297. DeclareDidRealVector1(x, n, (&hv)[n*n+(20+((n+15)*n)/2)+1*n]); \
  298. DeclareDidRealVector1(xInitial, n, (&hv)[n*n+(20+((n+15)*n)/2)+2*n]); \
  299. DeclareDidRealVector1(xJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+3*n]); \
  300. DeclareDidRealVector1(resJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+4*n]); \
  301. DeclareDidRealVector1(resJac2, n, (&hv)[n*n+(20+((n+15)*n)/2)+5*n]); \
  302. Real *hom1=(&hv)+n*n+(20+((n+15)*n)/2)+6*n;\
  303. Real *hom2=(&hv)+n*n+(20+((n+15)*n)/2)+6*n+nin;\
  304. Real homlocal,homlocaldelta,homlocalfail;\
  305. double lambda_=-2;\
  306. int *storedXP_=(&iv)+20+n;\
  307. int firstTime=1;\
  308. int* storedResetCounterP=(&iv)+21+n;\
  309. int veryFirstTime=ResetCounter_!=*(storedResetCounterP);\
  310. int veryFirstTime2=0;\
  311. int changePmatrix_=0;\
  312. int changePmatrixOld_=0;\
  313. int changePloop_=0;\
  314. int QNnl;int Qinfo,QNLnr,QiOpt,QInfRev;\
  315. DeclareDidRealMatrix2(Jac, n, n, hv);\
  316. DeclareDidRealVector2(res, n, (&hv)[n*n+(20+((n+15)*n)/2)+0*n]); \
  317. DeclareDidRealVector2(x, n, (&hv)[n*n+(20+((n+15)*n)/2)+1*n]); \
  318. DeclareDidRealVector2(xInitial, n, (&hv)[n*n+(20+((n+15)*n)/2)+2*n]); \
  319. DeclareDidRealVector2(xJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+3*n]); \
  320. DeclareDidRealVector2(resJac, n, (&hv)[n*n+(20+((n+15)*n)/2)+4*n]); \
  321. DeclareDidRealVector2(resJac2, n, (&hv)[n*n+(20+((n+15)*n)/2)+5*n]); \
  322. DYNassert_static(nhv==n*n+(20+((n+15)*n)/2)+2*nin+6*n && niv==22+n);\
  323. homlocal=-1;homlocaldelta=0;homlocalfail=0;\
  324. if (veryFirstTime) {int i;(*storedXP_)=0;for(i=0;i<n;i++) x##__internal[i]=0,res##__internal[i]=0;for(i=0;i<20+n;++i) Jac##__IWork[i]=0;for(i=0;i<20+((n+15)*n)/2;++i) Jac##__DWork[i]=0;}\
  325. again##nr: firstTime=1; againsecond##nr:\
  326. if (DymolaUserHomotopy) {lambda_=1-DymolaHomotopyLambda;if (DymolaHomotopyLambda==0) veryFirstTime=1;}\
  327. veryFirstTime2=(*(storedResetCounterP)==0);\
  328. *(storedResetCounterP)=ResetCounter_;\
  329. saved_jmp_buf_env = DYNGlobal_jmp_buf_env;\
  330. QNnl = n; \
  331. if (DYNEvent || ! DAEsolver_) { \
  332. QNLnr = nr; \
  333. QiOpt = numericJacobian+1; \
  334. QInfRev = -11+(numericJacobian?1:-DymolaNonLinearIterations_); \
  335. if ((!DymolaNewJacobian_ && !veryFirstTime) || !firstTime) QInfRev=-20-DymolaNonLinearIterations_-10*(1-DymolaAllowNewJacobianAnyway_);\
  336. if (inJacobian_ && !(*storedXP_)) {RealAssign(xJac,x); RealAssign(resJac,res); (*storedXP_)=1;\
  337. } else if ((*storedXP_)) {RealAssign(x,xJac);(*storedXP_)=inJacobian_;}\
  338. } else { \
  339. int i_;\
  340. QInfRev = 0;\
  341. for (i_=1; i_<=QNnl; i_++) \
  342. SetVector(x, i_, ((double*)X_)[i_+QBase]); \
  343. }
  344. #define DummyNonLinear(Jac,residue,m,n,Pvar,var,stateP, hv, nhv, iv, niv) \
  345. {\
  346. LIBDS_API int CheckP(const double*,double*,int,int,int*,const double*);\
  347. LIBDS_API void ComputeP(const double*,double*,int,int,int,int*,double*);\
  348. DeclareDidRealMatrix1(JacCopy_,n,m,hv);\
  349. int i_,j_;\
  350. int*Pivots_=&iv;\
  351. DeclareDidRealMatrix2(JacCopy_,n,m,hv);\
  352. DYNassert_static(nhv==n*m && niv==3*n);\
  353. if (Init_ || (DYNEvent && changePmatrixOld_)) {\
  354. int info;\
  355. int uno_=1,n_=n;\
  356. RealArray varP_=var;\
  357. ComputeP(&(GetMatrix(Jac,1,1)),&(GetMatrix(JacCopy_,1,1)),m,m,n,Pivots_,Pvar);\
  358. {int m1_=n-m;double d1_=1.0,d2_=0.0;\
  359. dgemv_("T",&n_,&m1_,&d1_,Pvar,&n_,varP_.data,&uno_,\
  360. &d2_,stateP,&uno_);}\
  361. for(i_=m+1;i_<=n;i_++) {double d_=-(stateP)[i_-(m+1)];\
  362. for(j_=1;j_<=n;j_++) d_+=(Pvar)[(i_-(m+1))*n+(j_-1)]*varP_.data[j_-1];\
  363. SetVector(residue,i_,d_);}\
  364. for(i_=m+1;i_<=n;i_++) for(j_=1;j_<=n;j_++) SetMatrix(Jac,i_,j_,(Pvar)[(i_-(m+1))*n+(j_-1)]);\
  365. Release();\
  366. changePmatrixOld_=0;\
  367. if (PrintEvent&(1<<13)) ReportDummySelection(varnames_,Pvar,DYNTime,m,n);\
  368. AnyREvent_=true;\
  369. } else if (CheckP(&(GetMatrix(Jac,1,1)),&(GetMatrix(JacCopy_,1,1)),m,n,Pivots_,Pvar)) changePmatrix_=1;\
  370. if ((PrintEvent&(1<<14))&&terminal()) ReportDummySelection(varnames_,Pvar,DYNTime,m,n);\
  371. }
  372. #define SetInit(x, i, j, var, val) \
  373. if (firstTime) \
  374. var = val; \
  375. if (firstTime && !(DYNEvent || ! DAEsolver_)) \
  376. SetMatrix(x, i, j, var); \
  377. else \
  378. var = GetMatrix(x, i, j)
  379. #define SetInitVector(x, i, var, val) \
  380. if (DymolaUserHomotopy && DymolaHomotopyLambda>0) {} else\
  381. if (firstTime) \
  382. var = val; \
  383. if ((DAEsolver_ && !DYNEvent) || !firstTime || inJacobian_) \
  384. var = GetVector(x, i); \
  385. else \
  386. SetVector(x, i, var); \
  387. #define SetInitVectorNH(x, i, var, val) \
  388. if (homlocal>0 || DymolaUserHomotopy && DymolaHomotopyLambda>0) var=GetVector(x, i); else\
  389. if (firstTime) \
  390. var = val; \
  391. if ((DAEsolver_ && !DYNEvent) || !firstTime || inJacobian_) \
  392. var = GetVector(x, i); \
  393. else \
  394. SetVector(x, i, var); \
  395. #define Residues \
  396. firstTime=0;\
  397. while (true) {\
  398. if (setjmp(DYNGlobal_jmp_buf_env.TheBuffer)!=0) {\
  399. PopAllMarks();\
  400. GlobalError_ = 0;\
  401. if (QInfRev>0) {\
  402. QInfRev+=100;\
  403. if (!(PrintEvent&(1<<10))) DymosimMessage("Non-linear solver will attempt to handle this problem.\n");\
  404. }\
  405. else {\
  406. if (!(PrintEvent&(1<<10))) DymosimMessage("First evaluation failed for non-linear solver.\n");\
  407. if (solverHandleEq_) EqRemember2Time_=-1e40;\
  408. if (!((*(DSE_STRUCT QiErr)||MixedFailFlag_)&&(QInfRev==0))) QInfRev=-1;\
  409. }\
  410. } else {\
  411. #define Jacobian(Jac) \
  412. if (QInfRev == 2 || QInfRev<=-11 && QInfRev>-20 || (DAEsolver_ && !DYNEvent && !inJacobian_)) {
  413. #if 1
  414. LIBDS_API void dymnon7_(int*qinfrev, int qiopt, int qnnl, double*qsol,double* qres,double* qjac,
  415. double qtol, double qtoldesired,
  416. int*qinfo, double*qd, int lqd, int*idum, int printevent, int inJacobian_, int qnlnr, double time,
  417. int*qnlfunc, int*qnljac, int qnlmax, const char*const*varnames,const double*nom,int*ierr___,const char*tag);
  418. #define DymNonlinear2(QInfRev,QiOpt,QNnl,QSol,QRes,QJac,Qtol,Qtol2,Qinfo,QD,LQD,DumI, \
  419. PrintEvent,QNLnr,Time,QNLfunc,QNLjac,QNLmax,ierr_,tag) {int i1_,i2_;\
  420. i1_ = LQD; \
  421. i2_ = QNLmax; \
  422. if (QNLnr > QNLmax) { \
  423. DymosimMessage("Internal error: The capacity for solving nonlinear systems of equations, QNLmax, needs to be increased"); \
  424. DYN_GOTOLEAVE; \
  425. } \
  426. dymnon7_(&QInfRev,QiOpt,QNnl,QSol,QRes,QJac,Qtol,Qtol2,&Qinfo,QD,i1_,DumI,\
  427. PrintEvent,inJacobian_,QNLnr,Time,QNLfunc,QNLjac,i2_,varnames_,nominal_,ierr_,tag);}
  428. #else
  429. LIBDS_API void dymnon6_(int*qinfrev, int qiopt, int qnnl, double*qsol,double* qres,double* qjac,
  430. double qtol, double qtoldesired,
  431. int*qinfo, double*qd, int lqd, int*idum, int printevent, int inJacobian_, int qnlnr, double time,
  432. int*qnlfunc, int*qnljac, int qnlmax, const char*const*varnames,const double*nom,int*ierr___);
  433. #define DymNonlinear2(QInfRev,QiOpt,QNnl,QSol,QRes,QJac,Qtol,Qtol2,Qinfo,QD,LQD,DumI, \
  434. PrintEvent,QNLnr,Time,QNLfunc,QNLjac,QNLmax,ierr_,tag) {int i1_,i2_;\
  435. i1_ = LQD; \
  436. i2_ = QNLmax; \
  437. if (QNLnr > QNLmax) { \
  438. DymosimMessage("Internal error: The capacity for solving nonlinear systems of equations, QNLmax, needs to be increased"); \
  439. DYN_GOTOLEAVE; \
  440. } \
  441. dymnon6_(&QInfRev,QiOpt,QNnl,QSol,QRes,QJac,Qtol,Qtol2,&Qinfo,QD,i1_,DumI,\
  442. PrintEvent,inJacobian_,QNLnr,Time,QNLfunc,QNLjac,i2_,varnames_,nominal_,ierr_);}
  443. #endif
  444. /*
  445. \
  446. if (QInfRev==0 && Qinfo==4) goto leave;
  447. */
  448. #define OverdeterminedNonLinear(Jac,Jac2,residue,residue2,m,n,m1,m2,var,hv,nhv) \
  449. {\
  450. LIBDS_API void CreateJacFull(const double*,double*,int,int,int,const int*);\
  451. LIBDS_API void ComputePfull(const double*,double*,int,int,int,int,int,int*,int*,double*,const double*,const double*);\
  452. LIBDS_API int CheckPfull(const double*,double*,int,int,int,int,int,int*,const int*);\
  453. DeclareDidRealMatrix1(JacCopy_,m,n,hv);\
  454. int i_,j_;\
  455. DeclareDidRealMatrix2(JacCopy_,m,n,hv);\
  456. DYNassert_static(nhv==n*m);\
  457. if (Init_ || (DYNEvent && changePmatrixOld_)) {\
  458. ComputePfull(&(GetMatrix(Jac2,1,1)),&(GetMatrix(JacCopy_,1,1)),m,m,n,m1,m2,IWork_+(m+n),IWork_,0,0,0);\
  459. changePmatrixOld_=0;\
  460. } else if (CheckPfull(&(GetMatrix(Jac2,1,1)),&(GetMatrix(JacCopy_,1,1)),m,m,n,m1,m2,IWork_+(m+n),IWork_)) changePmatrix_=1;\
  461. CreateJacFull(&(GetMatrix(Jac2,1,1)),&(GetMatrix(Jac,1,1)),m,m,n,IWork_);\
  462. } \
  463. } {\
  464. LIBDS_API void NonLinearRoutine(int,int,double*,const int*,const double*,const double*,const double*,const double*);\
  465. NonLinearRoutine(m,n,&(GetVector(residue,1)),IWork_,&(GetVector(residue2,1)),0,0,0);\
  466. #define OverdeterminedDummyNonLinear(Jac,Jac2,residue,residue2,l,m,n,m1,m2,Pvar,var,stateP,hv,nhv) \
  467. {\
  468. LIBDS_API void CreateJacFull(const double*,double*,int,int,int,const int*);\
  469. LIBDS_API void ComputePfull(const double*,double*,int,int,int,int,int,int*,int*,double*,const double*,const double*);\
  470. LIBDS_API int CheckPfull(const double*,double*,int,int,int,int,int,int*,const int*);\
  471. DeclareDidRealMatrix1(JacCopy_,m,n,hv);\
  472. int i_,j_;\
  473. DeclareDidRealMatrix2(JacCopy_,m,n,hv);\
  474. DYNassert_static(nhv==n*m);\
  475. if (Init_ || (DYNEvent && changePmatrixOld_)) {\
  476. RealArray varP_=var;\
  477. ComputePfull(&(GetMatrix(Jac2,1,1)),&(GetMatrix(JacCopy_,1,1)),l,m,n,m1,m2,IWork_+(l+n),IWork_,Pvar,varP_.data,stateP);\
  478. Release();\
  479. changePmatrixOld_=0;\
  480. if (PrintEvent&(1<<13)) ReportDummySelection(varnames_,Pvar,DYNTime,m,n);\
  481. AnyREvent_=true;\
  482. } else if (CheckPfull(&(GetMatrix(Jac2,1,1)),&(GetMatrix(JacCopy_,1,1)),l,m,n,m1,m2,IWork_+(l+n),IWork_)) changePmatrix_=1;\
  483. CreateJacFull(&(GetMatrix(Jac2,1,1)),&(GetMatrix(Jac,1,1)),l,m,n,IWork_);\
  484. } \
  485. } {\
  486. LIBDS_API void NonLinearRoutine(int,int,double*,const int*,const double*,const double*,const double*,const double*);\
  487. RealArray varP_=var;\
  488. NonLinearRoutine(m,n,&(GetVector(residue,1)),IWork_,&(GetVector(residue2,1)),Pvar,varP_.data,stateP);\
  489. Release();
  490. #define SolveNonLinearSystemOfEquationsInner(Jac, res, x, tag) \
  491. } \
  492. } DYNGlobal_jmp_buf_env=saved_jmp_buf_env;\
  493. if (!(QInfRev != 0 || ((DYNEvent && !Init_ && changePmatrix_)?(changePmatrixOld_=changePmatrix_,QInfRev=-1,changePmatrix_=0,changePloop_++<5):0)))\
  494. break;\
  495. if (DYNEvent || ! DAEsolver_) { \
  496. double Qtol1=Qtol;\
  497. double Qtol2=DymolaAimForHighAccuracy_ ? Dymola_min(EPS_*0.5,0.01*Qtol) : Qtol;\
  498. if (inJacobian_ && (*storedXP_)) RealSubtractAssign(res,res,resJac);\
  499. DymNonlinear2(QInfRev,QiOpt,QNnl,&(GetVector(x,1)),&(GetVector(res,1)),\
  500. &(GetMatrix(Jac,1,1)),Qtol1,Qtol2,Qinfo, \
  501. Jac##__DWork,Jac##__LDWork,Jac##__IWork,PrintEvent,QNLnr,DYNTime,QNLfunc,QNLjac,QNLmax,QiErr,tag); \
  502. if (*QiErr != 0) {*QiErr=0;QInfRev=0;DymosimError("Inner failed");}
  503. #define SolveNonLinearSystemOfEquations(Jac, res, x, tag) \
  504. } \
  505. } DYNGlobal_jmp_buf_env=saved_jmp_buf_env;\
  506. if (QInfRev == 0) {\
  507. if (DYNEvent && !Init_ && changePmatrix_) {\
  508. changePmatrixOld_=changePmatrix_;\
  509. QInfRev=-1;\
  510. changePmatrix_=0;\
  511. if (changePloop_++>=5) break;\
  512. } else break;\
  513. }\
  514. if (DYNEvent || ! DAEsolver_) { \
  515. double Qtol1=Qtol;\
  516. double Qtol2=DymolaAimForHighAccuracy_ ? Dymola_min(EPS_*0.5,0.01*Qtol) : Qtol;\
  517. if (inJacobian_ && (*storedXP_)) RealSubtractAssign(res,res,resJac);\
  518. DymNonlinear2(QInfRev,QiOpt,QNnl,&(GetVector(x,1)),&(GetVector(res,1)),\
  519. &(GetMatrix(Jac,1,1)),Qtol1,Qtol2,Qinfo, \
  520. Jac##__DWork,Jac##__LDWork,Jac##__IWork,PrintEvent,QNLnr,DYNTime,QNLfunc,QNLjac,QNLmax,QiErr,tag); \
  521. if (*QiErr != 0) DYN_GOTOLEAVE
  522. #define SolveNonLinearSystemOfEquationsNH(Jac, res, x, nr, tag) \
  523. } \
  524. } DYNGlobal_jmp_buf_env=saved_jmp_buf_env;\
  525. if (QInfRev == 0) {\
  526. if (DYNEvent && !Init_ && changePmatrix_) {\
  527. changePmatrixOld_=changePmatrix_;\
  528. QInfRev=-1;\
  529. changePmatrix_=0;\
  530. if (changePloop_++>=5) break;\
  531. } else break;\
  532. }\
  533. if (DYNEvent || ! DAEsolver_) { \
  534. double Qtol1=Qtol;\
  535. double Qtol2=DymolaAimForHighAccuracy_ ? Dymola_min(EPS_*0.5,0.01*Qtol) : Qtol;\
  536. if (inJacobian_ && (*storedXP_)) RealSubtractAssign(res,res,resJac);\
  537. DymNonlinear2(QInfRev,QiOpt,QNnl,&(GetVector(x,1)),&(GetVector(res,1)),\
  538. &(GetMatrix(Jac,1,1)),Qtol1,Qtol2,Qinfo, \
  539. Jac##__DWork,Jac##__LDWork,Jac##__IWork,PrintEvent,QNLnr,DYNTime,QNLfunc,QNLjac,QNLmax,QiErr,tag); \
  540. if (*QiErr && DYNEvent && homlocal==-1) { *QiErr=0;DymosimMessage("Trying homotopy");homlocal=0;homlocaldelta=0.125;goto again##nr;}\
  541. if (*QiErr && DYNEvent && homlocal>0 && homlocaldelta>1e-4) {*QiErr=0;DymosimMessage("Homotopy reducing");homlocal-=homlocaldelta;homlocalfail=homlocal;homlocaldelta/=2;homlocal+=homlocaldelta;goto again##nr;}\
  542. if (*QiErr != 0) DYN_GOTOLEAVE
  543. #define NonLinearSystemSave(a, nr) \
  544. if (homlocal==-1) {if (DYNEvent) hom1[nr]=a; else hom2[nr]=a;}\
  545. else a=hom1[nr]*homlocal+hom2[nr]*(1-homlocal);
  546. #define SolveNonLinearSystemOfEquationsInit(Jac, res, x, tag) \
  547. } \
  548. } DYNGlobal_jmp_buf_env=saved_jmp_buf_env;\
  549. if (!(QInfRev != 0 || ((DYNEvent && !Init_ && changePmatrix_)?(changePmatrixOld_=changePmatrix_,QInfRev=-1,changePmatrix_=0,changePloop_++<5):0)))\
  550. break;\
  551. if (DYNEvent || ! DAEsolver_) { \
  552. double Qtol1=Qtol;\
  553. double Qtol2=DymolaAimForHighAccuracy_ ? Dymola_min(EPS_*0.5,0.01*Qtol) : Qtol;\
  554. if (lambda_<0 && !inJacobian_) {Qtol1=Qtol2;}\
  555. if (lambda_==-2 && !inJacobian_ && (QInfRev==1 || QInfRev<-1)) {RealAssign(resJac,res);lambda_=-1;}\
  556. if (lambda_>0 && !DymolaUserHomotopy) {RealSubtractAssign(res,res,RealScale(resJac,lambda_));PopAllMarks();}\
  557. if (inJacobian_ && (*storedXP_)) RealSubtractAssign(res,res,resJac);\
  558. DymNonlinear2(QInfRev,QiOpt,QNnl,&(GetVector(x,1)),&(GetVector(res,1)),\
  559. &(GetMatrix(Jac,1,1)),Qtol1,Qtol2,Qinfo, \
  560. Jac##__DWork,Jac##__LDWork,Jac##__IWork,PrintEvent,QNLnr,DYNTime,QNLfunc,QNLjac,QNLmax,(DSE_STRUCT QiErr),tag); \
  561. if (*(DSE_STRUCT QiErr) != 0 && !(*(DSE_STRUCT QiErr)>=1 && *(DSE_STRUCT QiErr)<=4 && lambda_==-1)) goto leave
  562. #define SolveNonLinearSystemOfEquationsMixed(Jac, res, x, tag) \
  563. } \
  564. } DYNGlobal_jmp_buf_env=saved_jmp_buf_env;\
  565. if (!(QInfRev != 0 || ((DYNEvent && !Init_ && changePmatrix_)?(changePmatrixOld_=changePmatrix_,QInfRev=-1,changePmatrix_=0,changePloop_++<5):0)))\
  566. break;\
  567. if (DYNEvent || ! DAEsolver_) { \
  568. double Qtol1=Qtol;\
  569. double Qtol2=DymolaAimForHighAccuracy_ ? Dymola_min(EPS_*0.5,0.01*Qtol) : Qtol;\
  570. if (inJacobian_ && (*storedXP_)) RealSubtractAssign(res,res,resJac);\
  571. DymNonlinear2(QInfRev,QiOpt,QNnl,&(GetVector(x,1)),&(GetVector(res,1)),\
  572. &(GetMatrix(Jac,1,1)),Qtol1,Qtol2,Qinfo, \
  573. Jac##__DWork,Jac##__LDWork,Jac##__IWork,PrintEvent,QNLnr,DYNTime,QNLfunc,QNLjac,QNLmax,QiErr,tag); \
  574. if (*QiErr != 0) {MixedFailFlag_=*QiErr;*QiErr=0;QInfRev=0;}
  575. #define VerifyOverdeterminedResidual(res1, n1, res2, n2) \
  576. if (QInfRev == 0 && !(DYNEvent && !Init_ && changePmatrix_)) {\
  577. if (!inJacobian_) {\
  578. int i;double res2=0,res1=0;\
  579. for(i=1;i<=n1;++i) res1+=sqr(GetVector(res1, i));for(i=1;i<=n2;++i) res2+=sqr(GetVector(res2, i));\
  580. if (res2>res1*1000+Qtol*Qtol*10) {*QiErr=1;if (!(PrintEvent&(1<<10))) DymosimMessage("Too large residual for overdetermined system");DYN_GOTOLEAVE;}\
  581. }\
  582. }
  583. #define EndNonLinearSystemOfEquations(res, x) \
  584. } \
  585. triggerStepEvent_=triggerStepEvent_|| (changePmatrix_ && !DYNEvent);\
  586. } \
  587. if (DAEsolver_) {\
  588. int i_;\
  589. triggerStepEvent_=triggerStepEvent_|| (changePmatrix_ && !DYNEvent);\
  590. if (!DYNEvent) for (i_=1; i_<=QNnl; i_++) \
  591. ((double*)F_)[i_+QBase] = GetVector(res,i_); \
  592. else for (i_=1; i_<=QNnl; i_++) \
  593. ((double*)X_)[i_+QBase] = GetVector(x,i_); \
  594. }\
  595. }
  596. #define EndNonLinearSystemOfEquationsNH(res, x, nr) \
  597. } \
  598. triggerStepEvent_=triggerStepEvent_|| (changePmatrix_ && !DYNEvent);\
  599. } \
  600. if (DAEsolver_) {\
  601. int i_;\
  602. triggerStepEvent_=triggerStepEvent_|| (changePmatrix_ && !DYNEvent);\
  603. if (!DYNEvent) for (i_=1; i_<=QNnl; i_++) \
  604. ((double*)F_)[i_+QBase] = GetVector(res,i_); \
  605. else for (i_=1; i_<=QNnl; i_++) \
  606. ((double*)X_)[i_+QBase] = GetVector(x,i_); \
  607. }\
  608. if (homlocal!=-1 && homlocal!=1) {if (homlocaldelta<0.05 && homlocal>homlocalfail+4*homlocalfail) homlocaldelta*=2;homlocal+=homlocaldelta;if (homlocal>1) homlocal=1;goto again##nr;}\
  609. }
  610. #define EndNonLinearSystemOfEquationsInit(res, x,nr) \
  611. } \
  612. triggerStepEvent_=triggerStepEvent_|| (changePmatrix_ && !DYNEvent);\
  613. }\
  614. if (*(DSE_STRUCT QiErr)>=1 && *(DSE_STRUCT QiErr)<=4 && lambda_==-1) {*(DSE_STRUCT QiErr)=0;lambda_=1;if (!(PrintEvent&(1<<10))) DymosimMessage("Trying to solve non-linear system using global homotopy-method.");if (DymolaHomotopyUsed){DymolaUserHomotopy=1;GlobalError_=-997;goto leave;} goto again##nr;} \
  615. if (lambda_>0 && !DymolaHomotopyUsed) {lambda_-=0.1; if (lambda_-1e-3<0) lambda_=0;goto again##nr;}\
  616. }
  617. #define ModelicaPrintMatrixRows(Mat, nRows) \
  618. DymosimMessageDoubleMatrix(#Mat, &(GetMatrix(Mat,1,1)), nRows, \
  619. MatrixNrColumns(Mat), MatrixNrRows(Mat) )
  620. #define MixedSystemOfEquations(n,hv)\
  621. {\
  622. DeclareDidRealVector1(oldVector,n, hv); \
  623. int changeflag = 1;\
  624. int niter = 0;\
  625. double deltaTheta = 1e-3;\
  626. double deltaTheta2 = 1e-12;\
  627. DeclareDidRealVector2(oldVector,n, hv); \
  628. while (1) {\
  629. if (MixedFailFlag_&&DYNEvent&&!changeflag) {AnyEvent_=1;AnyDEvent_=1;MixedFailFlag_=0;AnyEventParameter_=1;break;}\
  630. if (!changeflag) break;\
  631. if (MixedFailFlag_&&(niter>0) && !(PrintEvent&(1<<10))) DymosimMessage("Fixed point iterating to handle problem.");\
  632. changeflag = 0;MixedFailFlag_ = 0;\
  633. ++niter;\
  634. if (niter > 13) {\
  635. if (PrintEvent&(1<<1)) DymosimMessageDouble("Fix point iteration did not converge at time :", DYNTime);\
  636. if (!AnyEvent_) MixedFailFlag_=1;\
  637. break;\
  638. }
  639. #define MixedInitialSystemOfEquations(n, hv)\
  640. {\
  641. DeclareDidRealVector1(oldVector,n, hv); \
  642. int changeflag = 1;\
  643. int niter = 0;\
  644. double deltaTheta = 1e-3;\
  645. double deltaTheta2 = 1e-12;\
  646. DeclareDidRealVector2(oldVector,n, hv); \
  647. while (changeflag) {\
  648. ++niter;\
  649. if (niter > 13) {\
  650. MixedFailFlag_=true;\
  651. if ((PrintEvent&(1<<1))||MixedFailFlag_&&!(PrintEvent&(1<<10))) DymosimMessageDouble("Fix point iteration did not converge at time :", DYNTime);\
  652. break;\
  653. } \
  654. if (MixedFailFlag_&& DymolaHomotopyUsed && !DymolaUserHomotopy) {if (!(PrintEvent&(1<<10))) DymosimMessage("Solving using global homotopy-method.");MixedFailFlag_=0;DymolaUserHomotopy=1;GlobalError_=-997;goto leave;}\
  655. if (MixedFailFlag_&&(niter>0) && !(PrintEvent&(1<<10))) DymosimMessage("Fixed point iterating to handle problem.");\
  656. changeflag = 0;MixedFailFlag_ = 0;
  657. #define EndMixedSystemOfEquations\
  658. }}}if (MixedFailFlag_) {*(DSE_STRUCT QiErr)=MixedFailFlag_;DYN_GOTOLEAVE;}}
  659. #define MixedModeStartBoolean \
  660. { int mixedModeFlag=(DYNEvent || !RootFinder_) && (niter>1);\
  661. int thetaIter=-1;int thetaIterFlag=1;double mixedModeTheta,mixedModeTheta2;\
  662. int thetaNr=0;\
  663. for(;thetaIterFlag!=0;thetaIter++) { \
  664. mixedModeTheta=mixedModeTheta2=1; \
  665. if (thetaIter>-1) {
  666. #define MixedModeInit(nr, hv) \
  667. } \
  668. if (mixedModeFlag) { \
  669. double *Qold_=&(hv);
  670. #define ThetaMixedCross(j,nr) \
  671. if (thetaIter==-1) DYNX(Qold_,j)=DYNX(Qenable_,nr+1) ? DYNX(QRel_,nr) : 0; \
  672. else if (DYNX(Qold_,j)*DYNX(QRel_,nr)<0) {\
  673. double th=DYNX(Qold_,j)/(DYNX(Qold_,j)-DYNX(QRel_,nr));\
  674. if (th<mixedModeTheta) {if(th<mixedModeTheta-deltaTheta2) mixedModeTheta2=mixedModeTheta;\
  675. mixedModeTheta=th;thetaNr=nr;}\
  676. else if (th<mixedModeTheta2-deltaTheta2 && th>mixedModeTheta+deltaTheta2) {mixedModeTheta2=th;}\
  677. }
  678. #define MixedModeEndBoolean \
  679. } \
  680. if (thetaIter==-1) continue; \
  681. if (thetaIterFlag==2) break; else thetaIterFlag=2;\
  682. if (mixedModeTheta<1-deltaTheta) {\
  683. changeflag=1;\
  684. mixedModeTheta=Dymola_min(mixedModeTheta+deltaTheta,(mixedModeTheta+mixedModeTheta2)/2);\
  685. if (PrintEvent&(1<<1)) DymosimMessageDouble("Shorter attempt for mixed equation system",mixedModeTheta);\
  686. } else {\
  687. mixedModeTheta=1;\
  688. thetaIterFlag=0;\
  689. }
  690. #define UpdateVariable(var, val)\
  691. {\
  692. int val1 = val;\
  693. if (!inJacobian_ && var != val1) {changeflag = 1;var = val1;if (PrintEvent&(1<<1)) VariableChanged(#var,val,DYNTime);}\
  694. }
  695. #define UpdateVariableNamed(var, varn, val)\
  696. {\
  697. int val1 = val;\
  698. if (!inJacobian_ && var != val1) {changeflag = 1;var = val1;if (PrintEvent&(1<<1)) VariableChanged(varn,val,DYNTime);}\
  699. }
  700. #define UpdateReal(var, nr) \
  701. if(mixedModeTheta<1) \
  702. var=GetVector(oldVector,nr)+(mixedModeTheta)*(var-GetVector(oldVector,nr));\
  703. SetVector(oldVector, nr, var);
  704. #if defined(DS_EMBEDDED)
  705. #define TranslatedEquations\
  706. dse_GetVariables(vars, sts);\
  707. sectioncondition = true;\
  708. {
  709. #define EndTranslatedEquations\
  710. PopAllMarks();\
  711. dse_SetVariables(vars, sts);\
  712. }
  713. #define ModelFunctionEnd() \
  714. return 0;finish: return 1;leave:return 2
  715. #else
  716. #define TranslatedEquations\
  717. sectioncondition = true;\
  718. {
  719. #define EndTranslatedEquations\
  720. PopAllMarks();\
  721. }
  722. #endif
  723. #define DefaultSection\
  724. }\
  725. sectioncondition = true;\
  726. {\
  727. #define InitialSection2\
  728. }\
  729. sectioncondition = initializationPhase_?initializationPhase_==2:(initial() && !continueSimulate_);\
  730. if (sectioncondition) {\
  731. *icall_ = 0;
  732. #define InitialSection3\
  733. }\
  734. sectioncondition = (initializationPhase_==1) || (initial() && !continueSimulate_);\
  735. if (sectioncondition) {\
  736. *icall_ = 0;
  737. #define InitialSection\
  738. }\
  739. sectioncondition = (initializationPhase_ || initialAlsoContinue()) && (DymolaOneIteration_<3);\
  740. if (sectioncondition) {\
  741. *icall_ = 0;
  742. #define InitialBoundSection\
  743. }\
  744. sectioncondition = (initializationPhase_ || initialAlsoContinue()) && (DymolaOneIteration_<3) && (!DymolaUserHomotopy || DymolaUserHomotopy && DymolaHomotopyLambda==0);\
  745. if (sectioncondition) {\
  746. *icall_ = 0;
  747. #define InitialStartSection2\
  748. }\
  749. sectioncondition = (initializationPhase_?initializationPhase_==2:(initial() && !continueSimulate_)) && (!DymolaUserHomotopy || DymolaHomotopyLambda<=0) && (DymolaOneIteration_<3);\
  750. if (sectioncondition) {\
  751. *icall_ = 0;
  752. #define InitialStartSection3\
  753. }\
  754. sectioncondition = ((initializationPhase_==1) || (initial() && !continueSimulate_)) && (!DymolaUserHomotopy || DymolaHomotopyLambda<=0) && (DymolaOneIteration_<3);\
  755. if (sectioncondition) {\
  756. *icall_ = 0;
  757. #define InitialStartSection\
  758. }\
  759. sectioncondition = (initializationPhase_ || initialAlsoContinue()) && (DymolaOneIteration_<3) && (!DymolaUserHomotopy || DymolaHomotopyLambda<=0);\
  760. if (sectioncondition) {\
  761. *icall_ = 0;
  762. #define EndInitialSection\
  763. if (DymolaUserHomotopy) {if (DymolaHomotopyLambda<1) {if (GlobalError_==0)GlobalError_=-996;goto leave;} else DymolaUserHomotopy=0;DymolaHomotopyLambda=1;}
  764. #define BoundParameterSection \
  765. }\
  766. sectioncondition = NewParameters_ && (!DymolaUserHomotopy || DymolaUserHomotopy && DymolaHomotopyLambda==0);\
  767. if (sectioncondition) {
  768. DYMOLA_STATIC void initializeData(double *time, double* X_, double* XD_, double* U_,
  769. double* DP_, int IP_[], Dymola_bool LP_[],
  770. double* F_, double* Y_, double* W_, double QZ_[],
  771. double duser_[], int iuser_[], void*cuser_[],
  772. int final_,int Init,int m_Event,int solverCall);
  773. DYMOLA_STATIC void initializeDataNew(double *time, double* X_, double* XD_, double* U_,
  774. double* DP_, int IP_[], Dymola_bool LP_[],
  775. double* F_, double* Y_, double* W_, double QZ_[],
  776. double duser_[], int iuser_[], void*cuser_[],struct DYNInstanceData*,
  777. int final_,int solverCall);
  778. #define InitializeData(fin) {\
  779. initializeDataNew(time, X_, XD_, U_, \
  780. DP_, IP_, LP_, \
  781. F_, Y_, W_, QZ_, \
  782. duser_, iuser_, cuser_, did_,\
  783. fin,fin&&(did_->DymolaEventOptional_var&&solverHandleEq_&&(*idemand_==4))); \
  784. }
  785. #define InitializeDataSolver() {\
  786. initializeDataNew(time, X_, XD_, U_, \
  787. DP_, IP_, LP_, \
  788. F_, Y_, W_, QZ_, \
  789. duser_, iuser_, cuser_, did_,\
  790. 0,1); \
  791. }
  792. #define StartDataBlock DYMOLA_STATIC void initializeData(double *time, double* X_, double* XD_, double* U_, \
  793. double* DP_, int IP_[], Dymola_bool LP_[], \
  794. double* F_, double* Y_, double* W_, double QZ_[], \
  795. double duser_[], int iuser_[], void*cuser_[],\
  796. int final_,int Init,int m_Event,int solverCall) {tempData.Init_var=Init;tempData.Event_var=m_Event;\
  797. initializeDataNew(time,X_,XD_,U_,DP_,IP_,LP_,F_,Y_,W_,QZ_,duser_,iuser_,cuser_,&tempData,final_,solverCall);}\
  798. DYMOLA_STATIC void initializeDataNew(double *time, double* X_, double* XD_, double* U_, \
  799. double* DP_, int IP_[], Dymola_bool LP_[], \
  800. double* F_, double* Y_, double* W_, double QZ_[], \
  801. double duser_[], int iuser_[], void*cuser_[], struct DYNInstanceData*did_,\
  802. int final_,int solverCall) {
  803. #define StartEqBlock if (solverCall?1:(Init_||(DYNEvent&&final_)||(!solverHandleEq_&&!inJacobian_&&final_))) {\
  804. if ((solverCall||(DYNEvent&&solverHandleEq_)) && *time>EqRemember2Time_) {int ii_;EqRemember1Time_=EqRemember2Time_;\
  805. for(ii_=0;ii_<SizeEq_;ii_++) EqRemember1_[ii_]=EqRemember2_[ii_];}\
  806. EqRemember2Time_=*time;
  807. DYMOLA_STATIC void UpdateInitVars(double *time, double* X_, double* XD_, double* U_,
  808. double* DP_, int IP_[], Dymola_bool LP_[],
  809. double* F_, double* Y_, double* W_, double QZ_[], double duser_[], int iuser_[], void*cuser_[],struct DYNInstanceData*did_);
  810. #define OutputSection\
  811. }\
  812. sectioncondition = ((*idemand_ >= 1 && *icall_ < 1) || (DYNEvent || *idemand_==4)) && (DymolaOneIteration_!=-1);\
  813. if (sectioncondition) {\
  814. *icall_ = 1;
  815. #define DynamicsSection\
  816. }\
  817. sectioncondition = ((*idemand_ >= 2 && *icall_ < 2) || (DYNEvent || *idemand_==4)) && (DymolaOneIteration_!=-1);\
  818. if (sectioncondition) {\
  819. *icall_ = 2;
  820. #define AcceptedSection\
  821. }\
  822. sectioncondition = ((*idemand_ >= 3 && *icall_ < 3) || (DYNEvent || *idemand_==4)) && (DymolaOneIteration_!=-1);\
  823. if (sectioncondition) {\
  824. *icall_ = 3;
  825. #define AcceptedSection1\
  826. }\
  827. sectioncondition = ((*idemand_ >= 3 && *icall_ < 3) || (DYNEvent || *idemand_==4)) && (DymolaOneIteration_!=-1);\
  828. if (sectioncondition) {\
  829. *icall_ = 3;
  830. #define ODEJacobianSection\
  831. }\
  832. sectioncondition = (did_->QJacobian_var || did_->QJacobianSparse_var);\
  833. if (sectioncondition) {\
  834. if (did_->QJacobian_var) {int i_;for(i_=0;i_<did_->QJacobianN_var*did_->QJacobianN_var;++i_) did_->QJacobian_var[i_]=0.0;}
  835. #define ODEBCDJacobianSection\
  836. sectioncondition = (did_->QBJacobian_var && did_->QCJacobian_var && did_->QDJacobian_var) || (did_->QJacobianSparse_var && did_->QSparseABCD_var);\
  837. if (sectioncondition && (did_->QBJacobian_var && did_->QCJacobian_var && did_->QDJacobian_var)) {int i_;\
  838. for(i_=0;i_<did_->QJacobianN_var*did_->QJacobianNU_var;++i_) did_->QBJacobian_var[i_]=0.0;\
  839. for(i_=0;i_<did_->QJacobianNY_var*did_->QJacobianN_var;++i_) did_->QCJacobian_var[i_]=0.0;\
  840. for(i_=0;i_<did_->QJacobianNY_var*did_->QJacobianNU_var;++i_) did_->QDJacobian_var[i_]=0.0;\
  841. }\
  842. if (sectioncondition)
  843. #define ODEJacobian(iz, r, c, v) (did_->QJacobian_var?did_->QJacobian_var+(r-1)+(c-1)*did_->QJacobianN_var:did_->QJacobianSparse_var+iz)[0] = v; if (did_->QJacobianSparse_var) {did_->QJacobianSparseR_var[iz]=r-1;did_->QJacobianSparseC_var[iz]=c-1;}
  844. #define ODEBJacobian(iz, r, c, v) (did_->QBJacobian_var?did_->QBJacobian_var+(r-1)+(c-1)*did_->QJacobianN_var:did_->QJacobianSparse_var+iz)[0]=v; if (did_->QJacobianSparse_var && did_->QSparseABCD_var) {did_->QJacobianSparseR_var[iz]=r-1;did_->QJacobianSparseC_var[iz]=c-1+AnalyticJacobianSize_;}
  845. #define ODECJacobian(iz, r, c, v) (did_->QCJacobian_var?did_->QCJacobian_var+(r-1)+(c-1)*did_->QJacobianNY_var:did_->QJacobianSparse_var+iz)[0]=v; if (did_->QJacobianSparse_var && did_->QSparseABCD_var) {did_->QJacobianSparseR_var[iz]=r-1+AnalyticJacobianSize_;did_->QJacobianSparseC_var[iz]=c-1;}
  846. #define ODEDJacobian(iz, r, c, v) (did_->QDJacobian_var?did_->QDJacobian_var+(r-1)+(c-1)*did_->QJacobianNY_var:did_->QJacobianSparse_var+iz)[0]=v; if (did_->QJacobianSparse_var && did_->QSparseABCD_var) {did_->QJacobianSparseR_var[iz]=r-1+AnalyticJacobianSize_;did_->QJacobianSparseC_var[iz]=c-1+AnalyticJacobianSize_;}
  847. /* ---------------------------------------------------- */
  848. /* Macros to build variable name table. */
  849. struct DeclarePhase;
  850. #if defined(Matlab5) || defined(Matlab51) || defined(SimStruct) || defined(DYMOLA_DSPACE) || defined(DYM2DS) || defined(FMU_SOURCE_CODE_EXPORT)
  851. #if !defined(DynSimStruct)
  852. #define DynSimStruct 1
  853. #endif
  854. #endif
  855. #define PreNonAliasDef(nr) DYMOLA_STATIC void declare__##nr(double x0_[],double dp_[],double du_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase);
  856. #define FuncStartNonAlias(nr) DYMOLA_STATIC void declare__##nr(double x0_[],double dp_[],double du_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase) {
  857. #if defined(DynSimStruct) || !defined(DYMOSIM)
  858. /* Not in Dymosim => cannot use blo-routines */
  859. #if GenerateResultInNonDymosim==2 || (GenerateResultInNonDymosim==1 && !(defined(RT) || defined(DYMOLA_DSPACE)))
  860. #include "GenerateResultInNonDymosim.h"
  861. /* Special code for generating result files from Matlab
  862. #define GenerateResultInMatlab 2
  863. - do this always
  864. #define GenerateResultInMatlab 1
  865. - only when running inside Matlab and not on realtime platforms
  866. */
  867. #define DeclareSParameter(par, descpar, ipar, val, mi, ma, w, typ, con) {0+(typ<<3)+(con<<5),par,val,0,0.0,0.0,w,ipar},
  868. #define DeclareParameter(par, descpar, ipar, val, mi, ma, w,typ,con) {1+(typ<<3)+(con<<5),par,descpar,val,mi, ma,w,ipar},
  869. #define DeclareState(x, descx, ix, val, mi, ma,w, typ,con) {2+(typ<<3)+(con<<5),x,descx,val,mi, ma, w, ix},
  870. #define DeclareDerivative(dx, descdx, val, mi, ma,w, typ,con) {3+(typ<<3)+(con<<5),dx,descdx,val,mi, ma, w},
  871. #define DeclareOutput(var, descvar, iy, val, mi, ma, w,typ, con) {4+(typ<<3)+(con<<5),var,descvar,val,mi, ma, w},
  872. #define DeclareInput(var, descvar, iu, val, mi, ma, w,typ, con) {5+(typ<<3)+(con<<5),var,descvar,val,mi, ma, w},
  873. #define DeclareVariable(var,descvar, val, mi, ma, w, typ, con) {6+(typ<<3)+(con<<5),var,descvar,val,mi, ma, w},
  874. #define DeclareAlias(name, description, aliasname, sign, sigtype, sigindex) {7+(sigtype<<3),name,description,sign,0.0,0.0,0,sigindex},
  875. #define DeclareAlias2(name, description, aliasname, sign, sigtype, sigindex, typ) {7+(sigtype<<3)+(typ<<6),name,description,sign,0.0,0.0,0,sigindex},
  876. #define PreNonAliasNew(nr) {declare__##nr(x0_,dp_,du_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  877. #define PreNonAlias(nr) {PreNonAliasDef(nr);declare__##nr(x0_,dp_,du_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  878. #define StartNonAlias(nr) static struct NonAlias_ nonalias_##nr []={
  879. #define EndNonAlias(nr) {100}}; FuncStartNonAlias(nr) \
  880. struct NonAlias_*nonalias_=nonalias_##nr;\
  881. int i_,imax_;\
  882. switch(phase ? phase->temp.declarePhase_ : 0) {\
  883. case 0: /* Handle literal start-values and parameters.*/\
  884. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  885. int t=nonalias_[i_].tag&7;\
  886. switch(t) {\
  887. case 0:if (cuser_) cuser_[nonalias_[i_].ix]=(void*)(nonalias_[i_].d);break;\
  888. case 1:if (dp_) dp_[nonalias_[i_].ix]=nonalias_[i_].val;break;\
  889. case 2:if (x0_) x0_[nonalias_[i_].ix]=nonalias_[i_].val;break;\
  890. default:break;\
  891. }}break;\
  892. case 11: /* Count items */\
  893. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  894. int storF=(nonalias_[i_].tag>>6)&(512|1024);\
  895. int stor=DYNStoreProtectedVariables || (storF==0 || storF==(512|1024));\
  896. int t=nonalias_[i_].tag&7;\
  897. switch(t) {\
  898. case 1:if(stor)phase->temp.isPublicP_[setDefaultP_]|=1;++setDefaultP_;break;\
  899. case 2:if(stor)phase->temp.isPublicX_[setDefaultX_]|=1;++setDefaultX_;break;\
  900. case 3:if(stor)phase->temp.isPublicXD_[setDefaultDX_]|=1;++setDefaultDX_;break;\
  901. case 6:if(stor)phase->temp.isPublicW_[setDefaultW_]|=1;++setDefaultW_;break;\
  902. case 7:{\
  903. static const int mapToO[8]={0,2,5,4,0,6,3,1};\
  904. int kind=mapToO[(nonalias_[i_].tag>>3)&7];\
  905. if (kind==6 && stor) phase->temp.isPublicW_[nonalias_[i_].ix]|=2;\
  906. if (kind==2 && stor) phase->temp.isPublicX_[nonalias_[i_].ix]|=2;\
  907. if (kind==3 && stor) phase->temp.isPublicXD_[nonalias_[i_].ix]|=2;\
  908. if (kind==1 && stor) phase->temp.isPublicP_[nonalias_[i_].ix]|=2;\
  909. }\
  910. default:break;\
  911. }}break;\
  912. case 1: /* Count items */\
  913. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  914. int t=nonalias_[i_].tag&7;\
  915. int storF=(nonalias_[i_].tag>>6)&(512|1024);\
  916. int stor=DYNStoreProtectedVariables||(storF==0 || storF==(512|1024));\
  917. if (t>=1 && t<=6) {\
  918. if (!DYNStoreProtectedVariables && ((t==6 && !phase->temp.isPublicW_[setDefaultW_++])||(t==2 && !phase->temp.isPublicX_[setDefaultX_++])||(t==3 && !phase->temp.isPublicXD_[setDefaultDX_++])||(t==1 && !phase->temp.isPublicP_[setDefaultP_++]))) {phase->temp.offsets_[t]++;continue;}\
  919. } else if(t==7) {\
  920. static const int mapToO[8]={0,2,5,4,0,6,3,1};\
  921. int kind=mapToO[(nonalias_[i_].tag>>3)&7];\
  922. if (!DYNStoreProtectedVariables && (kind==6||kind==2||kind==3||kind==1) && !stor) continue;\
  923. if (!DYNStoreProtectedVariables && (kind==6 && phase->temp.isPublicW_[nonalias_[i_].ix]==2)) {phase->temp.isPublicW_[nonalias_[i_].ix]=4;continue;}\
  924. if (!DYNStoreProtectedVariables && (kind==2 && phase->temp.isPublicX_[nonalias_[i_].ix]==2)) {phase->temp.isPublicX_[nonalias_[i_].ix]=4;continue;}\
  925. if (!DYNStoreProtectedVariables && (kind==3 && phase->temp.isPublicXD_[nonalias_[i_].ix]==2)) {phase->temp.isPublicXD_[nonalias_[i_].ix]=4;continue;}\
  926. if (!DYNStoreProtectedVariables && (kind==1 && phase->temp.isPublicP_[nonalias_[i_].ix]==2)) {phase->temp.isPublicP_[nonalias_[i_].ix]=4;continue;}\
  927. }\
  928. switch(t) {\
  929. case 1:*((phase->temp.offsets_[t])++)= - ++(phase->temp.countConst_);break;\
  930. case 2:*((phase->temp.offsets_[t])++)= ++(phase->temp.countNonConst_);break;\
  931. case 3:*((phase->temp.offsets_[t])++)=++(phase->temp.countNonConst_);break;\
  932. case 4:case 5:case 6:if (nonalias_[i_].tag&32) *(phase->temp.offsets_[t]++)= - ++(phase->temp.countConst_);else *((phase->temp.offsets_[t])++) = ++(phase->temp.countNonConst_);break;\
  933. case 7:++(phase->temp.countAlias_);break;\
  934. default:break;\
  935. }}break;\
  936. case 3:/* Add names, info */\
  937. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  938. int t=nonalias_[i_].tag&7;\
  939. int data=-1,offset,sgn=1;\
  940. int storF=(nonalias_[i_].tag>>6)&(512|1024);\
  941. int stor=DYNStoreProtectedVariables||(storF==0 || storF==(512|1024));\
  942. if (t>=1 && t<=7) {\
  943. if (!DYNStoreProtectedVariables && (t==6||t==2||t==3||t==1) && !stor) {phase->temp.offsets_[t]++;continue;}\
  944. if (t==7) {\
  945. static const int mapToO[8]={0,2,5,4,0,6,3,1};\
  946. int kind=mapToO[(nonalias_[i_].tag>>3)&7];\
  947. assert(kind!=0);\
  948. if (!DYNStoreProtectedVariables && (kind==6||kind==2||kind==3||kind==1) && !stor) continue;\
  949. offset=phase->temp.baseoffsets_[kind][nonalias_[i_].ix];\
  950. if (nonalias_[i_].val<0) sgn=-1;\
  951. } else offset=*((phase->temp.offsets_[t])++);\
  952. if (offset>0) {data=2;}else{offset=-offset;data=1;}\
  953. }\
  954. if (data!=-1) {\
  955. phase->temp.trajNames_[phase->temp.infoCount_]=nonalias_[i_].n;\
  956. phase->temp.trajDesc_[phase->temp.infoCount_]=nonalias_[i_].d;\
  957. phase->temp.trajInfo_[phase->temp.infoCount_+phase->totalInfoCount*0]=data;\
  958. phase->temp.trajInfo_[phase->temp.infoCount_+phase->totalInfoCount*1]=sgn*(offset+1);\
  959. phase->temp.trajInfo_[phase->temp.infoCount_+phase->totalInfoCount*2]=0;\
  960. phase->temp.trajInfo_[phase->temp.infoCount_+phase->totalInfoCount*3]=-1;\
  961. ++(phase->temp.infoCount_);\
  962. }\
  963. }break;\
  964. case 5: /* Update constants*/\
  965. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  966. int t=nonalias_[i_].tag&7;\
  967. if (!DYNStoreProtectedVariables && ((t==6 && !phase->temp.isPublicW_[setDefaultW_++])||(t==2 && !phase->temp.isPublicX_[setDefaultX_++])||(t==3 && !phase->temp.isPublicXD_[setDefaultDX_++])||(t==1 && !phase->temp.isPublicP_[setDefaultP_++]))) {++(phase->temp.offsets_[t]);++(phase->temp.pointers_[t]);continue;}\
  968. if (t>=1 && t<=6) {\
  969. if (*(phase->temp.offsets_[t])<0) \
  970. phase->temp.resultPart_[2* - *(phase->temp.offsets_[t])+1] =phase->temp.resultPart_[2* - *(phase->temp.offsets_[t])] = (float)(*(phase->temp.pointers_[t]));\
  971. ++(phase->temp.offsets_[t]);\
  972. ++(phase->temp.pointers_[t]);\
  973. }\
  974. }break;\
  975. case 7:/*Update non-constants */\
  976. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  977. int t=nonalias_[i_].tag&7;\
  978. if (t>=1 && t<=6) {\
  979. if (!DYNStoreProtectedVariables && ((t==6 && !phase->temp.isPublicW_[setDefaultW_++])||(t==2 && !phase->temp.isPublicX_[setDefaultX_++])||(t==3 && !phase->temp.isPublicXD_[setDefaultDX_++])||(t==1 && !phase->temp.isPublicP_[setDefaultP_++]))) {++(phase->temp.offsets_[t]);++(phase->temp.pointers_[t]);continue;}\
  980. if (*(phase->temp.offsets_[t])>0) \
  981. phase->temp.resultPart_[*(phase->temp.offsets_[t])] = (float)(*(phase->temp.pointers_[t]));\
  982. ++(phase->temp.offsets_[t]);\
  983. ++(phase->temp.pointers_[t]);\
  984. }\
  985. }break;\
  986. default:break;\
  987. }
  988. #else
  989. #define DeclareParameter(par, descpar, ipar, val, mi, ma, w,typ,con) if (dp_) dp_[ipar]=val;
  990. #define DeclareSParameter(par, descpar, ipar, val, mi, ma, w,typ,con) if (cuser_) cuser_[ipar]=(const char*)(val);
  991. #define DeclareState(x, descx, ix, val, mi, ma,w, typ, con) if (x0_) x0_[ix]=val;
  992. #define DeclareDerivative(dx, descdx, val, mi, ma,w, typ, con)
  993. #define DeclareOutput(var, descvar, iy, val, mi, ma, w,typ, con)
  994. #define DeclareInput(var, descvar, iu, val, mi, ma, w,typ, con) if (du_) du_[iu]=val;
  995. #define DeclareVariable(var,descvar, val, mi, ma, w, typ, con)
  996. #define DeclareAlias(name, description, aliasname, sign, sigtype, sigindex)
  997. #define DeclareAlias2(name, description, aliasname, sign, sigtype, sigindex, typ)
  998. #define PreNonAliasNew(nr) {declare__##nr(x0_,dp_,du_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  999. #define PreNonAlias(nr) {PreNonAliasDef(nr);declare__##nr(x0_,dp_,du_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  1000. #define StartNonAlias(nr) FuncStartNonAlias(nr)
  1001. #define EndNonAlias(nr)
  1002. #endif
  1003. #define DeclareConstant(c)
  1004. #define StartAlias(nr) void declarea__##nr(double x0_[],double dp_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase) {
  1005. #define EndAlias(nr)
  1006. #define PreAlias(nr) {void declarea__##nr(double x0_[],double dp_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase);declarea__##nr(x0_,dp_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  1007. #else
  1008. #define DeclareSParameter(par,descpar,ipar,val,mi,ma,w,typ,con) {0+(typ<<3)+(con<<5),par,val,0,0.0,0.0,w,ipar},
  1009. #define DeclareParameter(par, descpar, ipar, val, mi, ma, w,typ,con) {1+(typ<<3)+(con<<5),par,descpar,val,mi, ma,w,ipar},
  1010. #define DeclareState(x, descx, ix, val, mi, ma,w, typ,con) {2+(typ<<3)+(con<<5),x,descx,val,mi, ma, w, ix},
  1011. #define DeclareDerivative(dx, descdx, val, mi, ma,w, typ,con) {3+(typ<<3)+(con<<5),dx,descdx,val,mi, ma, w},
  1012. #define DeclareOutput(var, descvar, iy, val, mi, ma, w,typ, con) {4+(typ<<3)+(con<<5),var,descvar,val,mi, ma, w},
  1013. #define DeclareInput(var, descvar, iu, val, mi, ma, w,typ, con) {5+(typ<<3)+(con<<5),var,descvar,val,mi, ma, w},
  1014. #define DeclareVariable(var,descvar, val, mi, ma, w, typ, con) {6+(typ<<3)+(con<<5),var,descvar,val,mi, ma, w},
  1015. #define DeclareAlias(name, description, aliasname, sign, sigtype, sigindex) {7+(sigtype<<3),name,description,sign,0.0,0.0,0,sigindex},
  1016. #define DeclareAlias2(name, description, aliasname, sign, sigtype, sigindex, typ) {7+(sigtype<<3)+(typ<<6),name,description,sign,0.0,0.0,0,sigindex},
  1017. #define PreNonAliasDef(nr) DYMOLA_STATIC void declare__##nr(double x0_[],double dp_[],double du_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase);
  1018. #define PreNonAliasNew(nr) {declare__##nr(x0_,dp_,du_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  1019. #define PreNonAlias(nr) {PreNonAliasDef(nr);declare__##nr(x0_,dp_,du_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  1020. #define StartNonAlias(nr) static struct NonAlias_ nonalias_##nr []={
  1021. #define EndNonAlias(nr) {100}}; FuncStartNonAlias(nr) \
  1022. LIBDS_API void blo3val(int,int,double,double,double,double,int);\
  1023. int c1_,c2_,c3_;double d1_;int i_,imax_;\
  1024. struct NonAlias_*nonalias_=nonalias_##nr;\
  1025. c1_=c2_=c3_=0;d1_=0;\
  1026. if (!setDefault_) {\
  1027. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  1028. switch(nonalias_[i_].tag&7) {\
  1029. case 0:blo3psd_(nonalias_[i_].n,nonalias_[i_].d);cuser_[nonalias_[i_].ix]=(void*)(nonalias_[i_].d);break;\
  1030. case 1:blo3pd_(nonalias_[i_].n,nonalias_[i_].d);dp_[nonalias_[i_].ix]=nonalias_[i_].val;if (nonalias_[i_].tag>=64) blo3pt_(nonalias_[i_].tag>>6);break;\
  1031. case 2:blo3sx_(nonalias_[i_].n,nonalias_[i_].d);x0_[nonalias_[i_].ix]=nonalias_[i_].val;if (nonalias_[i_].tag>=64) blo3st_(nonalias_[i_].tag>>6);break;\
  1032. case 3:blo3sd_(nonalias_[i_].n,nonalias_[i_].d);if (nonalias_[i_].tag>=64) blo3st_(nonalias_[i_].tag>>6);break;\
  1033. case 4:blo3sy_(nonalias_[i_].n,nonalias_[i_].d);if (nonalias_[i_].tag&32) {blo3co_(nonalias_[i_].val);};if (nonalias_[i_].tag>=64) blo3st_(nonalias_[i_].tag>>6);break;\
  1034. case 5:blo3su_(nonalias_[i_].n,nonalias_[i_].d);if (nonalias_[i_].tag&32) {blo3co_(nonalias_[i_].val);};if (nonalias_[i_].tag>=64) blo3st_(nonalias_[i_].tag>>6);break;\
  1035. case 6:blo3sw_(nonalias_[i_].n,nonalias_[i_].d);if (nonalias_[i_].tag&32) {blo3co_(nonalias_[i_].val);};if (nonalias_[i_].tag>=64) blo3st_(nonalias_[i_].tag>>6);break;\
  1036. case 7:blo3sa_(nonalias_[i_].n,nonalias_[i_].d,(nonalias_[i_].tag>>3)&7,nonalias_[i_].ix+1,(nonalias_[i_].val>0)?1:-1);if (nonalias_[i_].tag>=64) blo3st_(nonalias_[i_].tag>>6);break;\
  1037. default:break;\
  1038. }\
  1039. }} else {\
  1040. for(i_=0,imax_=sizeof(nonalias_##nr)/sizeof(nonalias_##nr [0])-1;i_<imax_;++i_){\
  1041. int num=0;int sect=nonalias_[i_].tag&7;\
  1042. if (sect!=7 && sect!=0) {switch(sect) {\
  1043. case 1:num=++setDefaultP_;break;\
  1044. case 2:num=++setDefaultX_;break;\
  1045. case 3:num=++setDefaultDX_;break;\
  1046. case 4:num=++setDefaultY_;break;\
  1047. case 5:num=++setDefaultU_;break;\
  1048. case 6:num=++setDefaultW_;break;\
  1049. default:break;\
  1050. }blo3val(sect,num,nonalias_[i_].val,nonalias_[i_].mi,nonalias_[i_].ma,nonalias_[i_].w,(nonalias_[i_].tag>>3)&3);}\
  1051. }}\
  1052. #define PreAlias(nr) {void declarea__##nr(double x0_[],double dp_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase);declarea__##nr(x0_,dp_,cuser_,QiErr,setDefault_,setDefaultX_,setDefaultU_,setDefaultY_,setDefaultP_,setDefaultDX_,setDefaultW_,phase);}}
  1053. #define StartAlias(nr) static struct NonAlias_ alias_##nr []={
  1054. #define EndAlias(nr) {100}}; void declarea__##nr(double x0_[],double dp_[],void*cuser_[],int*QiErr,int setDefault_,int setDefaultX_,int setDefaultU_,int setDefaultY_,int setDefaultP_,int setDefaultDX_,int setDefaultW_, struct DeclarePhase*phase) {\
  1055. LIBDS_API void blo3val(int,int,double,double,double,double,int);\
  1056. int c1_,c2_,c3_;double d1_;int i_,imax_;\
  1057. struct NonAlias_*alias_=alias_##nr;\
  1058. c1_=c2_=c3_=0;d1_=0;\
  1059. if (!setDefault_) {\
  1060. for(i_=0,imax_=sizeof(alias_##nr)/sizeof(alias_##nr [0])-1;i_<imax_;++i_){\
  1061. switch(alias_[i_].tag&7) {\
  1062. case 0:blo3psd_(nonalias_[i_].n,nonalias_[i_].d);cuser_[nonalias_[i_].ix]=(void*)(nonalias_[i_].d);break;\
  1063. case 1:blo3pd_(alias_[i_].n,alias_[i_].d);dp_[alias_[i_].ix]=alias_[i_].val;if (alias_[i_].tag>=64) blo3pt_(alias_[i_].tag>>6);break;\
  1064. case 2:blo3sx_(alias_[i_].n,alias_[i_].d);x0_[alias_[i_].ix]=alias_[i_].val;if (alias_[i_].tag>=64) blo3st_(alias_[i_].tag>>6);break;\
  1065. case 3:blo3sd_(alias_[i_].n,alias_[i_].d);if (alias_[i_].tag>=64) blo3st_(alias_[i_].tag>>6);break;\
  1066. case 4:blo3sy_(alias_[i_].n,alias_[i_].d);if (alias_[i_].tag&32) {blo3co_(alias_[i_].val);};if (alias_[i_].tag>=64) blo3st_(alias_[i_].tag>>6);break;\
  1067. case 5:blo3su_(alias_[i_].n,alias_[i_].d);if (alias_[i_].tag&32) {blo3co_(alias_[i_].val);};if (alias_[i_].tag>=64) blo3st_(alias_[i_].tag>>6);break;\
  1068. case 6:blo3sw_(alias_[i_].n,alias_[i_].d);if (alias_[i_].tag&32) {blo3co_(alias_[i_].val);};if (alias_[i_].tag>=64) blo3st_(alias_[i_].tag>>6);break;\
  1069. case 7:blo3sa_(alias_[i_].n,alias_[i_].d,(alias_[i_].tag>>3)&7,alias_[i_].ix+1,(alias_[i_].val>0)?1:-1);break;\
  1070. default:break;\
  1071. }\
  1072. }} else {\
  1073. for(i_=0,imax_=sizeof(alias_##nr)/sizeof(alias_##nr [0])-1;i_<imax_;++i_){\
  1074. int num=0;int sect=alias_[i_].tag&7;\
  1075. if (sect!=7 && sect!=0) {switch(sect) {\
  1076. case 1:num=++setDefaultP_;break;\
  1077. case 2:num=++setDefaultX_;break;\
  1078. case 3:num=++setDefaultDX_;break;\
  1079. case 4:num=++setDefaultY_;break;\
  1080. case 5:num=++setDefaultU_;break;\
  1081. case 6:num=++setDefaultW_;break;\
  1082. default:break;\
  1083. }blo3val(sect,num,alias_[i_].val,alias_[i_].mi,alias_[i_].ma,alias_[i_].w,(alias_[i_].tag>>3)&3);}\
  1084. }}\
  1085. #endif
  1086. #if defined(DYMOLA_DSPACE) || defined(DynSimStruct) && DymolaAutoRemoveAuxiliaries_
  1087. #define AcceptedSection2\
  1088. }sectioncondition=0; if (0) {*icall_=2;
  1089. #elif DymolaAutoRemoveAuxiliaries_
  1090. #define AcceptedSection2\
  1091. } sectioncondition=sectioncondition && DymolaStoreAuxiliaries_; if (sectioncondition) {
  1092. #else
  1093. #define AcceptedSection2
  1094. #endif
  1095. #define CrossingSection\
  1096. }\
  1097. sectioncondition = (*idemand_ >= 4 && *icall_ < 4) || (DYNEvent || *idemand_==4);\
  1098. if (sectioncondition) {\
  1099. *icall_ = 4;
  1100. #if !defined(DYMOSIM)
  1101. #define SetInitVectorSimple(x, i, var, val) \
  1102. if (veryFirstTime && lambda_<-1) \
  1103. var = val; \
  1104. if ((firstTime || ! DAEsolver_) && !inJacobian_) \
  1105. SetVector(x, i, var); \
  1106. else \
  1107. var = GetVector(x, i)
  1108. #define SetInitVectorSimpleNH(x, i, var, val) \
  1109. if (veryFirstTime && lambda_<-1) \
  1110. var = val; \
  1111. if ((firstTime || ! DAEsolver_) && !inJacobian_) \
  1112. SetVector(x, i, var); \
  1113. else \
  1114. var = GetVector(x, i)
  1115. #else
  1116. #define SetInitVectorSimpleOld(x, i, var, val) \
  1117. if (veryFirstTime && (!DymolaUserHomotopy || DymolaUserHomotopy && DymolaHomotopyLambda==0)) var=val;\
  1118. if ((firstTime || ! DAEsolver_) && !inJacobian_) \
  1119. SetVector(x, i, var); \
  1120. else \
  1121. var = GetVector(x, i)
  1122. #define SetInitVectorSimple(x, i, var, val) \
  1123. if (veryFirstTime && (!DymolaUserHomotopy || DymolaUserHomotopy && DymolaHomotopyLambda==0)) {\
  1124. if (veryFirstTime2) SetVector(xInitial, i, var);else var = GetVector(xInitial, i);\
  1125. }\
  1126. if (firstTime || ! DAEsolver_) \
  1127. SetVector(x, i, var); \
  1128. else \
  1129. var = GetVector(x, i)
  1130. #define SetInitVectorSimpleNH(x, i, var, val) \
  1131. if (veryFirstTime && !(homlocal>0 || DymolaUserHomotopy && DymolaHomotopyLambda>0)) var=val;\
  1132. if ((firstTime || ! DAEsolver_) && !inJacobian_) \
  1133. SetVector(x, i, var); \
  1134. else \
  1135. var = GetVector(x, i)
  1136. #endif
  1137. #if defined(DYMOLA_DSPACE) || defined(NO_FILE)
  1138. #define InitializeModes(datfile,Modes,nModes) {nModes=0;}
  1139. #if 0
  1140. /* Change to #if 1 to see modes in CPUClk */
  1141. #define AddMode(Modes,nModes,Mode) { \
  1142. int j; \
  1143. unsigned int cnt = 0; \
  1144. for(j = 1; j <= MatrixNrRows(Modes); j++) \
  1145. cnt = (cnt << 1) | (GetVector(Mode,j) != 0); \
  1146. CPUClk = cnt; \
  1147. }
  1148. #else
  1149. #define AddMode(Modes,nModes,Mode)
  1150. #endif
  1151. #define OutputModes
  1152. #else
  1153. /* To handle modes */
  1154. #define AddMode(Modes,nModes,Mode) {\
  1155. int i,j;\
  1156. int doAppend=(nModes<MaxModes);\
  1157. for(i=1;doAppend&&(i<=nModes);i++) {\
  1158. int allSame=1;\
  1159. for(j=1;allSame&&(j<=MatrixNrRows(Modes));j++) \
  1160. allSame=GetMatrix(Modes,j,i)==GetVector(Mode,j);\
  1161. doAppend=!allSame;\
  1162. }\
  1163. if (doAppend) {\
  1164. nModes++;\
  1165. for(j=1;j<=MatrixNrRows(Modes);j++)\
  1166. SetMatrix(Modes,j,nModes,GetVector(Mode,j)); \
  1167. }\
  1168. }
  1169. #define InitializeModes(datfile,Modes,nModes) {\
  1170. Amatrix bigModes; AclassRead c[1];\
  1171. bigModes.name="bigModes"; bigModes.nrow=MatrixNrRows(Modes);\
  1172. bigModes.ncol=-MatrixNrColumns(Modes); bigModes.type=doubleMatrix; bigModes.data.d=Modes.data;\
  1173. c[0].matrix=&bigModes; c[0].req=1; c[0].rowDim=0; c[0].colDim=0; c[0].rowIndex=0; c[0].colIndex=0; c[0].onFile=0;\
  1174. nModes=0;\
  1175. if (amatReadAll(datfile,"NoClass",(char*)0,c,1)==0) {\
  1176. nModes=bigModes.ncol;\
  1177. } else {\
  1178. DymosimMessage(amatError);\
  1179. }\
  1180. }
  1181. #define OutputModes(datfile,mofile,newmodel,origmodel,pre,Modes,nModes,nModesOriginal) {\
  1182. if (datfile) {\
  1183. Amatrix bigModes;\
  1184. bigModes.name="bigModes"; bigModes.nrow=MatrixNrRows(Modes);\
  1185. bigModes.ncol=nModes; bigModes.type=doubleMatrix; bigModes.data.d=Modes.data;\
  1186. amatWrite(datfile,amatBinary,bigModes);\
  1187. }\
  1188. if (mofile) {FILE *f=fopen(mofile,"w");\
  1189. if (f) {\
  1190. int i,j,jmax=MatrixNrRows(Modes);\
  1191. fprintf(f,"// Automatically constructed mode variables\n\n");\
  1192. fprintf(f,"model %s\n\n",newmodel);\
  1193. fprintf(f," extends %s;\n\n",origmodel);\
  1194. fprintf(f," %s\n\n",pre);\
  1195. fprintf(f," Real bigModes[%d,%d]={",nModes,jmax);\
  1196. for(i=1;i<=nModes;i++) {fprintf(f,"\n { ");for(j=1;j<=jmax;j++) \
  1197. fprintf(f,"%s%g",(j==1)?"":", ",GetMatrix(Modes,j,i));fprintf(f,(i==nModes)?"}":"},");}\
  1198. fprintf(f," };\n\n");\
  1199. fprintf(f,"end %s;\n\n",newmodel);\
  1200. }\
  1201. fclose(f);}\
  1202. if (nModes>nModesOriginal) DymosimMessage("Found additional modes, please recompile model");\
  1203. }
  1204. #include <bloutil.h>
  1205. #ifdef Dymola_Include_MT
  1206. /*
  1207. A C-program for MT19937, with initialization improved 2002/1/26.
  1208. Coded by Takuji Nishimura and Makoto Matsumoto.
  1209. Before using, initialize the state by using init_genrand(seed)
  1210. or init_by_array(init_key, key_length).
  1211. Copyright (C) 1997 - 2002, Makoto Matsumoto and Takuji Nishimura,
  1212. All rights reserved.
  1213. Redistribution and use in source and binary forms, with or without
  1214. modification, are permitted provided that the following conditions
  1215. are met:
  1216. 1. Redistributions of source code must retain the above copyright
  1217. notice, this list of conditions and the following disclaimer.
  1218. 2. Redistributions in binary form must reproduce the above copyright
  1219. notice, this list of conditions and the following disclaimer in the
  1220. documentation and/or other materials provided with the distribution.
  1221. 3. The names of its contributors may not be used to endorse or promote
  1222. products derived from this software without specific prior written
  1223. permission.
  1224. THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
  1225. "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
  1226. LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
  1227. A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
  1228. CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
  1229. EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
  1230. PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
  1231. PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
  1232. LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
  1233. NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
  1234. SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  1235. Any feedback is very welcome.
  1236. http://www.math.sci.hiroshima-u.ac.jp/~m-mat/MT/emt.html
  1237. email: m-mat @ math.sci.hiroshima-u.ac.jp (remove space)
  1238. Modified to include prefix; added code for using time to randomize values (and print it)
  1239. and removed unused functions.
  1240. */
  1241. /* Period parameters */
  1242. #define Dymola_MT_N 624
  1243. #define Dymola_MT_M 397
  1244. #define Dymola_MT_MATRIX_A 0x9908b0dfUL /* constant vector a */
  1245. #define Dymola_MT_UPPER_MASK 0x80000000UL /* most significant w-r bits */
  1246. #define Dymola_MT_LOWER_MASK 0x7fffffffUL /* least significant r bits */
  1247. static unsigned int Dymola_MT_mt[Dymola_MT_N]; /* the array for the state vector */
  1248. static int Dymola_MT_mti=Dymola_MT_N+1; /* mti==N+1 means mt[N] is not initialized */
  1249. /* initializes mt[N] with a seed */
  1250. static void Dymola_MT_init_genrand(unsigned int s)
  1251. {
  1252. Dymola_MT_mt[0]= s & 0xffffffffUL;
  1253. for (Dymola_MT_mti=1; Dymola_MT_mti<Dymola_MT_N; Dymola_MT_mti++) {
  1254. Dymola_MT_mt[Dymola_MT_mti] =
  1255. (1812433253UL * (Dymola_MT_mt[Dymola_MT_mti-1] ^ (Dymola_MT_mt[Dymola_MT_mti-1] >> 30)) + Dymola_MT_mti);
  1256. /* See Knuth TAOCP Vol2. 3rd Ed. P.106 for multiplier. */
  1257. /* In the previous versions, MSBs of the seed affect */
  1258. /* only MSBs of the array mt[]. */
  1259. /* 2002/01/09 modified by Makoto Matsumoto */
  1260. Dymola_MT_mt[Dymola_MT_mti] &= 0xffffffffUL;
  1261. /* for >32 bit machines */
  1262. }
  1263. }
  1264. /* initialize by an array with array-length */
  1265. /* init_key is the array for initializing keys */
  1266. /* key_length is its length */
  1267. /* slight change for C++, 2004/2/26 */
  1268. static void Dymola_MT_init_by_array(unsigned int init_key[], int key_length)
  1269. {
  1270. int i, j, k;
  1271. Dymola_MT_init_genrand(19650218UL);
  1272. i=1; j=0;
  1273. k = (Dymola_MT_N>key_length ? Dymola_MT_N : key_length);
  1274. for (; k; k--) {
  1275. Dymola_MT_mt[i] = (Dymola_MT_mt[i] ^ ((Dymola_MT_mt[i-1] ^ (Dymola_MT_mt[i-1] >> 30)) * 1664525UL))
  1276. + init_key[j] + j; /* non linear */
  1277. Dymola_MT_mt[i] &= 0xffffffffUL; /* for WORDSIZE > 32 machines */
  1278. i++; j++;
  1279. if (i>=Dymola_MT_N) { Dymola_MT_mt[0] = Dymola_MT_mt[Dymola_MT_N-1]; i=1; }
  1280. if (j>=key_length) j=0;
  1281. }
  1282. for (k=Dymola_MT_N-1; k; k--) {
  1283. Dymola_MT_mt[i] = (Dymola_MT_mt[i] ^ ((Dymola_MT_mt[i-1] ^ (Dymola_MT_mt[i-1] >> 30)) * 1566083941UL))
  1284. - i; /* non linear */
  1285. Dymola_MT_mt[i] &= 0xffffffffUL; /* for WORDSIZE > 32 machines */
  1286. i++;
  1287. if (i>=Dymola_MT_N) { Dymola_MT_mt[0] = Dymola_MT_mt[Dymola_MT_N-1]; i=1; }
  1288. }
  1289. Dymola_MT_mt[0] = 0x80000000UL; /* MSB is 1; assuring non-zero initial array */
  1290. }
  1291. #include <time.h>
  1292. #ifdef _MSC_VER
  1293. #include <process.h>
  1294. #endif
  1295. static void Dymola_MT_init_default(void) {
  1296. char str[100];
  1297. #if 0
  1298. Dymola_MT_init_genrand(5489UL); /* a default initial seed is used */
  1299. #else
  1300. unsigned int s =(unsigned int)(time(0));
  1301. #ifdef _MSC_VER
  1302. s+=(unsigned int)(_getpid())*10235489UL;
  1303. #endif
  1304. Dymola_MT_init_genrand(s);
  1305. DymosimMessageInt("Random number seed for MT19937:",s);
  1306. #endif
  1307. }
  1308. /* generates a random number on [0,0xffffffff]-interval */
  1309. static unsigned int Dymola_MT_genrand_int32(void)
  1310. {
  1311. unsigned int y;
  1312. static unsigned int mag01[2]={0x0UL, Dymola_MT_MATRIX_A};
  1313. /* mag01[x] = x * MATRIX_A for x=0,1 */
  1314. if (Dymola_MT_mti >= Dymola_MT_N) { /* generate N words at one time */
  1315. int kk;
  1316. if (Dymola_MT_mti == Dymola_MT_N+1) /* if init_genrand() has not been called, */
  1317. Dymola_MT_init_default(); /* a default initial seed is used */
  1318. for (kk=0;kk<Dymola_MT_N-Dymola_MT_M;kk++) {
  1319. y = (Dymola_MT_mt[kk]&Dymola_MT_UPPER_MASK)|(Dymola_MT_mt[kk+1]&Dymola_MT_LOWER_MASK);
  1320. Dymola_MT_mt[kk] = Dymola_MT_mt[kk+Dymola_MT_M] ^ (y >> 1) ^ mag01[y & 0x1UL];
  1321. }
  1322. for (;kk<Dymola_MT_N-1;kk++) {
  1323. y = (Dymola_MT_mt[kk]&Dymola_MT_UPPER_MASK)|(Dymola_MT_mt[kk+1]&Dymola_MT_LOWER_MASK);
  1324. Dymola_MT_mt[kk] = Dymola_MT_mt[kk+(Dymola_MT_M-Dymola_MT_N)] ^ (y >> 1) ^ mag01[y & 0x1UL];
  1325. }
  1326. y = (Dymola_MT_mt[Dymola_MT_N-1]&Dymola_MT_UPPER_MASK)|(Dymola_MT_mt[0]&Dymola_MT_LOWER_MASK);
  1327. Dymola_MT_mt[Dymola_MT_N-1] = Dymola_MT_mt[Dymola_MT_M-1] ^ (y >> 1) ^ mag01[y & 0x1UL];
  1328. Dymola_MT_mti = 0;
  1329. }
  1330. y = Dymola_MT_mt[Dymola_MT_mti++];
  1331. /* Tempering */
  1332. y ^= (y >> 11);
  1333. y ^= (y << 7) & 0x9d2c5680UL;
  1334. y ^= (y << 15) & 0xefc60000UL;
  1335. y ^= (y >> 18);
  1336. return y;
  1337. }
  1338. /* generates a random number on [0,1) with 53-bit resolution*/
  1339. static double Dymola_MT_genrand_res53(void)
  1340. {
  1341. unsigned int a=Dymola_MT_genrand_int32()>>5, b=Dymola_MT_genrand_int32()>>6;
  1342. return(a*67108864.0+b)*(1.0/9007199254740992.0);
  1343. }
  1344. /* These real versions are due to Isaku Wada, 2002/01/09 added */
  1345. /* End of MT19937*/
  1346. #endif
  1347. #ifndef DYMOLA_TIMES
  1348. #define DYMOLA_TIMES
  1349. struct DymolaTimes {
  1350. int num;
  1351. double maxim;
  1352. double minim;
  1353. double total;
  1354. int numAccum;
  1355. double maximAccum;
  1356. double minimAccum;
  1357. double totalAccum;
  1358. const char*name;
  1359. };
  1360. #endif
  1361. #if defined(DYMOLA_DSPACE) || defined(NO_FILE) || defined(FMU_SOURCE_CODE_EXPORT) || defined(LABCAR)
  1362. #define DymolaStartTimer(x)
  1363. #define DymolaEndTimer(x)
  1364. #define DymolaEndTimerName(x,n)
  1365. #define DymolaResetTimer(x) 0
  1366. #else
  1367. double DymolaTimerCounterSince(double*,int);
  1368. extern void DymolaOnInterrupt(void);
  1369. extern int DymolaNoInterrupt(void);
  1370. static void dymolaEndTimer(int num,struct DymolaTimes*dt,double Time,double*start,const char*name,double*tz,int tz_len,int*tz_cnt) {
  1371. double diff=DymolaTimerCounterSince(start,1);
  1372. if (num==0) {
  1373. DymolaOnInterrupt();
  1374. }
  1375. if (!dt) return; /* Error */
  1376. #if !defined(DymosimRealTimePriority_)
  1377. if (dt->num<=10 && 2*diff<dt->minim && diff>0) {
  1378. dt->num=0;
  1379. dt->numAccum=0;
  1380. dt->total=0;
  1381. dt->totalAccum=0;
  1382. }
  1383. #endif
  1384. if (dt->num==0) {
  1385. dt->minim=diff;
  1386. dt->maxim=diff;
  1387. dt->name=name;
  1388. } else {
  1389. #if !defined(DymosimRealTimePriority_)
  1390. if (diff>2000*dt->maxim && dt->maxim>0)
  1391. return;
  1392. #endif
  1393. if (diff>dt->maxim) dt->maxim=diff;
  1394. if (diff<dt->minim) dt->minim=diff;
  1395. }
  1396. dt->total+=diff;
  1397. #if defined(DymosimRealTimePriority_)
  1398. if (num==0 && tz && tz_cnt && 2*(*tz_cnt)+2<tz_len) {
  1399. if (tz[2*(*tz_cnt)]!=Time)
  1400. ++(*tz_cnt);
  1401. tz[2*(*tz_cnt)]=Time;
  1402. tz[2*(*tz_cnt)+1]+=diff;
  1403. }
  1404. #endif
  1405. dt->num++;
  1406. if (dt->numAccum==0) {
  1407. dt->maximAccum=diff;
  1408. dt->minimAccum=diff;
  1409. } else {
  1410. if (diff>dt->maximAccum) dt->maximAccum=diff;
  1411. if (diff<dt->minimAccum) dt->minimAccum=diff;
  1412. }
  1413. dt->totalAccum+=diff;
  1414. dt->numAccum++;
  1415. }
  1416. #define DymolaStartTimer(x) ((x==0)&&((DymolaNoInterrupt()))),DymolaTimerCounterSince(did_->DymolaStartTimers_vec+x,0)
  1417. #define DymolaEndTimer(x) dymolaEndTimer(x,did_->DymolaTimerStructs_vec+x,DYNTime,did_->DymolaStartTimers_vec+x,"",did_->DymolaTimeZero_vec,did_->DymolaTimeZeroLength_var,&(did_->DymolaTimecounter_var))
  1418. #define DymolaEndTimerName(x,n) dymolaEndTimer(x,did_->DymolaTimerStructs_vec+x,DYNTime,did_->DymolaStartTimers_vec+x,n,did_->DymolaTimeZero_vec,did_->DymolaTimeZeroLength_var,&(did_->DymolaTimecounter_var))
  1419. #define DymolaResetTimer(x) did_->DymolaTimerStructs_vec[x].totalAccum=did_->DymolaTimerStructs_vec[x].num=did_->DymolaTimerStructs_vec[x].numAccum=0
  1420. #endif
  1421. #endif
  1422. #endif