/*! \fn updateInnerEquation * * This function updates inner equation with the current x. * * \param [ref] [data] * [in] [sysNumber] index of corresponding non-linear system */ int updateInnerEquation(void **dataIn, int sysNumber, int discrete) { DATA *data = (DATA*) ((void**)dataIn[0]); threadData_t *threadData = (threadData_t*) ((void**)dataIn[1]); NONLINEAR_SYSTEM_DATA* nonlinsys = &(data->simulationInfo->nonlinearSystemData[sysNumber]); int success = 0; /* solve non continuous at discrete points*/ if(discrete) { data->simulationInfo->solveContinuous = 0; } /* try */ #ifndef OMC_EMCC MMC_TRY_INTERNAL(simulationJumpBuffer) #endif /* call residual function */ nonlinsys->residualFunc((void*) dataIn, nonlinsys->nlsx, nonlinsys->resValues, (int*)&nonlinsys->size); /* replace extrapolated values by current x for discrete step */ memcpy(nonlinsys->nlsxExtrapolation, nonlinsys->nlsx, nonlinsys->size*(sizeof(double))); success = 1; /*catch */ #ifndef OMC_EMCC MMC_CATCH_INTERNAL(simulationJumpBuffer) #endif if (!success) { warningStreamPrint(LOG_STDOUT, 0, "Non-Linear Solver try to handle a problem with a called assert."); } if(discrete) { data->simulationInfo->solveContinuous = 1; } return success; }
/*! \fn solve non-linear systems * * \param [in] [data] * \param [in] [sysNumber] index of corresponding non-linear system * * \author wbraun */ int solve_nonlinear_system(DATA *data, threadData_t *threadData, int sysNumber) { void *dataAndThreadData[2] = {data, threadData}; int success = 0, saveJumpState; NONLINEAR_SYSTEM_DATA* nonlinsys = &(data->simulationInfo.nonlinearSystemData[sysNumber]); struct dataNewtonAndHybrid *mixedSolverData; data->simulationInfo.currentNonlinearSystemIndex = sysNumber; /* enable to avoid division by zero */ data->simulationInfo.noThrowDivZero = 1; ((DATA*)data)->simulationInfo.solveContinuous = 1; rt_ext_tp_tick(&nonlinsys->totalTimeClock); if(data->simulationInfo.discreteCall) { double *fvec = malloc(sizeof(double)*nonlinsys->size); int success = 0; #ifndef OMC_EMCC /* try */ MMC_TRY_INTERNAL(simulationJumpBuffer) #endif ((DATA*)data)->simulationInfo.solveContinuous = 0; nonlinsys->residualFunc((void*) dataAndThreadData, nonlinsys->nlsx, fvec, (int*)&nonlinsys->size); ((DATA*)data)->simulationInfo.solveContinuous = 1; success = 1; #ifndef OMC_EMCC /*catch */ MMC_CATCH_INTERNAL(simulationJumpBuffer) #endif if (!success) { warningStreamPrint(LOG_STDOUT, 0, "Non-Linear Solver try to handle a problem with a called assert."); } free(fvec); }
/*! \fn solve non-linear systems * * \param [in] [data] * \param [in] [sysNumber] index of corresponding non-linear system * * \author wbraun */ int solve_nonlinear_system(DATA *data, threadData_t *threadData, int sysNumber) { void *dataAndThreadData[2] = {data, threadData}; int success = 0, saveJumpState; NONLINEAR_SYSTEM_DATA* nonlinsys = &(data->simulationInfo->nonlinearSystemData[sysNumber]); struct dataNewtonAndHybrid *mixedSolverData; data->simulationInfo->currentNonlinearSystemIndex = sysNumber; /* enable to avoid division by zero */ data->simulationInfo->noThrowDivZero = 1; ((DATA*)data)->simulationInfo->solveContinuous = 1; rt_ext_tp_tick(&nonlinsys->totalTimeClock); /* value extrapolation */ infoStreamPrint(LOG_NLS_EXTRAPOLATE, 1, "############ Start new iteration for system %d at time at %g ############", sysNumber, data->localData[0]->timeValue); printValuesListTimes((VALUES_LIST*)nonlinsys->oldValueList); /* if list is empty use current start values */ if (listLen(((VALUES_LIST*)nonlinsys->oldValueList)->valueList)==0) { //memcpy(nonlinsys->nlsxOld, nonlinsys->nlsx, nonlinsys->size*(sizeof(double))); //memcpy(nonlinsys->nlsxExtrapolation, nonlinsys->nlsx, nonlinsys->size*(sizeof(double))); memcpy(nonlinsys->nlsx, nonlinsys->nlsxOld, nonlinsys->size*(sizeof(double))); } else { /* get extrapolated values */ getValues((VALUES_LIST*)nonlinsys->oldValueList, data->localData[0]->timeValue, nonlinsys->nlsxExtrapolation, nonlinsys->nlsxOld); memcpy(nonlinsys->nlsx, nonlinsys->nlsxOld, nonlinsys->size*(sizeof(double))); } if(data->simulationInfo->discreteCall) { double *fvec = malloc(sizeof(double)*nonlinsys->size); int success = 0; #ifndef OMC_EMCC /* try */ MMC_TRY_INTERNAL(simulationJumpBuffer) #endif ((DATA*)data)->simulationInfo->solveContinuous = 0; nonlinsys->residualFunc((void*) dataAndThreadData, nonlinsys->nlsx, fvec, (int*)&nonlinsys->size); ((DATA*)data)->simulationInfo->solveContinuous = 1; success = 1; memcpy(nonlinsys->nlsxExtrapolation, nonlinsys->nlsx, nonlinsys->size*(sizeof(double))); #ifndef OMC_EMCC /*catch */ MMC_CATCH_INTERNAL(simulationJumpBuffer) #endif if (!success) { warningStreamPrint(LOG_STDOUT, 0, "Non-Linear Solver try to handle a problem with a called assert."); } free(fvec); }