OOFEM 3.0
Loading...
Searching...
No Matches
dustmat.C
Go to the documentation of this file.
1/*
2 *
3 * ##### ##### ###### ###### ### ###
4 * ## ## ## ## ## ## ## ### ##
5 * ## ## ## ## #### #### ## # ##
6 * ## ## ## ## ## ## ## ##
7 * ## ## ## ## ## ## ## ##
8 * ##### ##### ## ###### ## ##
9 *
10 *
11 * OOFEM : Object Oriented Finite Element Code
12 *
13 * Copyright (C) 1993 - 2025 Borek Patzak
14 *
15 *
16 *
17 * Czech Technical University, Faculty of Civil Engineering,
18 * Department of Structural Mechanics, 166 29 Prague, Czech Republic
19 *
20 * This library is free software; you can redistribute it and/or
21 * modify it under the terms of the GNU Lesser General Public
22 * License as published by the Free Software Foundation; either
23 * version 2.1 of the License, or (at your option) any later version.
24 *
25 * This program is distributed in the hope that it will be useful,
26 * but WITHOUT ANY WARRANTY; without even the implied warranty of
27 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
28 * Lesser General Public License for more details.
29 *
30 * You should have received a copy of the GNU Lesser General Public
31 * License along with this library; if not, write to the Free Software
32 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
33 */
34
35#include "dustmat.h"
36
37#include "floatarray.h"
38#include "floatmatrix.h"
40#include "gausspoint.h"
41#include "intarray.h"
44#include "datastream.h"
45#include "contextioerr.h"
46#include "mathfem.h"
47#include "classfactory.h"
48
49namespace oofem {
51
52DustMaterialStatus :: DustMaterialStatus(GaussPoint *gp, double q0) :
54{
55 stressVector.resize(6);
56 strainVector.resize(6);
57 tempStressVector.resize(6);
58 tempStrainVector.resize(6);
59 q = q0;
60}
61
62
63void
64DustMaterialStatus :: initTempStatus()
65{
66 // Call the function of the parent class to initialize the variables defined there.
67 StructuralMaterialStatus :: initTempStatus();
69 tempQ = q;
71}
72
73void
74DustMaterialStatus :: updateYourself(TimeStep *tStep)
75{
76 // Call the corresponding function of the parent class to update variables defined there.
77 StructuralMaterialStatus :: updateYourself(tStep);
79 q = tempQ;
81}
82
83void
84DustMaterialStatus :: printOutputAt(FILE *file, TimeStep *tStep) const
85{
86 // Call the corresponding function of the parent class to print variables defined there.
87 StructuralMaterialStatus :: printOutputAt(file, tStep);
88
89 fprintf(file, "\tstatus { ");
90
91 // print status flag
92 switch ( stateFlag ) {
93 case DustMaterialStatus :: DM_Elastic:
94 fprintf(file, " Elastic");
95 break;
96 case DustMaterialStatus :: DM_Yielding1:
97 fprintf(file, " Yielding1");
98 break;
99 case DustMaterialStatus :: DM_Yielding2:
100 fprintf(file, " Yielding2");
101 break;
102 case DustMaterialStatus :: DM_Yielding3:
103 fprintf(file, " Yielding3");
104 break;
105 case DustMaterialStatus :: DM_Unloading:
106 fprintf(file, " Unloading");
107 break;
108 }
109
110 fprintf(file, ", plasticStrains ");
111 for ( auto &val : this->givePlasticStrain() ) {
112 fprintf( file, " %.4e", val );
113 }
114
115 fprintf(file, ", q %.4e", q);
116
117 fprintf(file, "}\n");
118}
119
120void
121DustMaterialStatus :: saveContext(DataStream &stream, ContextMode mode)
122{
123 StructuralMaterialStatus :: saveContext(stream, mode);
124}
125
126
127void
128DustMaterialStatus :: restoreContext(DataStream &stream, ContextMode mode)
129{
130 StructuralMaterialStatus :: restoreContext(stream, mode);
131}
132
133
134
135// *************************************************************
136// *** CLASS DUST MATERIAL ***
137// *************************************************************
138
139
140DustMaterial :: DustMaterial(int n, Domain *d) : StructuralMaterial(n, d),
141 LEMaterial(n, d)
142{
143}
144
145
146void
147DustMaterial :: initializeFrom(InputRecord &ir)
148{
149 // call the corresponding service of structural material
150 StructuralMaterial :: initializeFrom(ir);
151 // call the corresponding service for the linear elastic material
152 this->LEMaterial.initializeFrom(ir);
153
154 // instanciate the variables defined in DustMaterial
155 ft = 3e6;
156 x0 = 150e6;
157 rEll = .5;
158 beta = .008e-6;
159 theta = .32;
160 alpha = 44e6;
161 lambda = 34e6;
162 wHard = .1;
163 dHard = .0003e-6;
164 mStiff = 0.;
165 newtonTol = 1e-8;
166 newtonIter = 200;
167
180
181 // check parameters admissibility
182 if ( ft < 0 ) {
183 throw ValueInputException(ir, _IFT_DustMaterial_ft, "must be positive");
184 }
185
186 if ( x0 < 0 ) {
187 throw ValueInputException(ir, _IFT_DustMaterial_x0, "must be positive");
188 }
189
190 if ( rEll < 0 ) {
191 throw ValueInputException(ir, _IFT_DustMaterial_rEll, "must be positive");
192 }
193
194 if ( theta < 0 ) {
195 throw ValueInputException(ir, _IFT_DustMaterial_theta, "must be positive");
196 }
197
198 if ( beta < 0 ) {
199 throw ValueInputException(ir, _IFT_DustMaterial_beta, "must be positive");
200 }
201
202 if ( lambda < 0 ) {
203 throw ValueInputException(ir, _IFT_DustMaterial_lambda, "must be positive");
204 }
205
206 if ( alpha < lambda ) {
207 throw ValueInputException(ir, _IFT_DustMaterial_alpha, "must be greater than lambda");
208 }
209
210 x0 = -x0; // compressive strength is negative, although on input it is a positive number
211
212 hardeningType = 0;
214
215 q0 = x0;
216 solveQ0(q0);
217}
218
220DustMaterial :: giveRealStressVector_3d(const FloatArrayF<6> &strain,
221 GaussPoint *gp, TimeStep *tStep) const
222{
223 auto status = static_cast< DustMaterialStatus * >( this->giveStatus(gp) );
224
225 // Initialize temp variables for this Gauss point
226 this->initTempStatus(gp);
227
228 // subtract stress-independent part of strain
229 auto thermalStrain = this->computeStressIndependentStrainVector_3d(gp, tStep, VM_Total);
230 auto strainVectorR = strain - thermalStrain;
231
232 // perform the local stress return and update the history variables
233 performStressReturn(gp, strainVectorR);
234
235 // copy total strain vector to the temp status
236 status->letTempStrainVectorBe(strain);
237
238 // pass the correct form of stressVector to giveRealStressVector
239 return status->giveTempStressVector();
240}
241
242void
243DustMaterial :: performStressReturn(GaussPoint *gp, const FloatArrayF<6> &strain) const
244{
245 auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
246
247 // compute total strain components
248 //auto [strainDeviator, volumetricStrain] = computeDeviatoricVolumetricSplit(strain); // c++17
249 auto tmp = computeDeviatoricVolumetricSplit(strain);
250 auto strainDeviator = tmp.first;
251 auto volumetricStrain = tmp.second;
252
253 // compute trial elastic strains
254 auto plasticStrain = status->givePlasticStrain();
255
256 //auto [plasticStrainDeviator, volumetricPlasticStrain] = computeDeviatoricVolumetricSplit(plasticStrain); // c++17
257 auto tmp2 = computeDeviatoricVolumetricSplit(plasticStrain);
258 auto plasticStrainDeviator = tmp2.first;
259 auto volumetricPlasticStrain = tmp2.second;
260
261 double volumetricElasticStrain = volumetricStrain - volumetricPlasticStrain;
262 auto elasticStrainDeviator = strainDeviator - plasticStrainDeviator;
263
264 // compute trial stresses
265 double bulkModulus, shearModulus;
266 computeAndSetBulkAndShearModuli(bulkModulus, shearModulus, gp);
267 double volumetricStress = 3. * bulkModulus * volumetricElasticStrain;
268 FloatArrayF<6> stressDeviator = {2 * elasticStrainDeviator[0], 2 * elasticStrainDeviator[1], 2 * elasticStrainDeviator[2],
269 elasticStrainDeviator[3], elasticStrainDeviator[4], elasticStrainDeviator[5]};
270 stressDeviator *= shearModulus;
271
272 // norm of trial stress deviator
273 double rho = computeSecondCoordinate(stressDeviator);
274 double i1 = 3 * volumetricStress;
275 double f1, f2, f3, q, tempQ;
276 q = tempQ = status->giveQ();
277 f1 = yieldFunction1(rho, i1);
278 f2 = yieldFunction2(rho, i1, q);
279 f3 = yieldFunction3(i1);
280
281 // actual stress return
282 double lambda = 0.;
284 double feft = functionFe(ft);
285 double auxModulus = 2 * shearModulus / ( 9 * bulkModulus );
286 double temp = feft - auxModulus * ( i1 - ft ) / functionFeDI1(ft);
287
288 if ( f1 > 0 && i1 >= q && rho >= temp ) { // yield function 1
289 status->letTempStateFlagBe(DustMaterialStatus :: DM_Yielding1);
290 performF1return(i1, rho, gp);
291 tempQ = status->giveTempQ();
292 lambda = ( rho - functionFe( functionI1(q, tempQ, i1, bulkModulus) ) ) / ( 2 * shearModulus );
293 m = computePlastStrainDirM1(stressDeviator, rho, i1, q);
294 } else if ( f2 > 0 && i1 < q ) { // yield function 2
295 status->letTempStateFlagBe(DustMaterialStatus :: DM_Yielding2);
296 performF2return(i1, rho, gp);
297 tempQ = status->giveTempQ();
298 lambda = computeDeltaGamma2(tempQ, q, i1, bulkModulus);
299 m = computePlastStrainDirM2(stressDeviator, rho, i1, tempQ);
300 } else if ( f3 > 0 && rho < temp ) { // yield function 3
301 status->letTempStateFlagBe(DustMaterialStatus :: DM_Yielding3);
302 double fFeFt = functionFe(ft);
303 double fFeDqFt = functionFeDI1(ft);
304 double b = fFeFt - 2 * shearModulus / ( 9 * bulkModulus ) * ( i1 - ft ) - ( 1 + fFeDqFt ) * rho;
305 double c = -fFeFt / ( 9 * bulkModulus ) * ( i1 - ft );
306 lambda = 1 / ( 4 * shearModulus ) * ( -b + sqrt(b * b - 8 * shearModulus * c) );
307 double deltaVolumetricPlasticStrain = 3 * ( 1 - ( 1 + fFeDqFt ) * rho / fFeFt ) * lambda;
308 if ( volumetricPlasticStrain + deltaVolumetricPlasticStrain < -.5 * wHard ) {
309 deltaVolumetricPlasticStrain = -.5 * wHard - volumetricPlasticStrain;
310 }
311
312 if ( q <= 0.0 ) {
313 computeQFromPlastVolEps(tempQ, q, deltaVolumetricPlasticStrain);
314 }
315
316 status->letTempQBe(tempQ);
317 m = computePlastStrainDirM3(stressDeviator, rho, i1, tempQ);
318 } else { // elastic case
319 int stateFlag = status->giveStateFlag();
320 if ( ( stateFlag == DustMaterialStatus :: DM_Unloading ) || ( stateFlag == DustMaterialStatus :: DM_Elastic ) ) {
321 status->letTempStateFlagBe(DustMaterialStatus :: DM_Elastic);
322 } else {
323 status->letTempStateFlagBe(DustMaterialStatus :: DM_Unloading);
324 }
325 }
326
327 if ( lambda < 0 ) {
328 OOFEM_ERROR("TODO");
329 }
330
331 // compute correct stress
332 m *= lambda;
333 plasticStrain += m;
334
335 //auto [mDeviator, mVol] = computeDeviatoricVolumetricSplit(m); // c++17
337 auto mDeviator = tmp3.first;
338 auto mVol = tmp3.second;
339
340 i1 -= 3 * bulkModulus * mVol;
341 volumetricStress = i1 / 3.;
342 stressDeviator += (-2 * shearModulus) * mDeviator;
343
344 // compute full stresses from deviatoric and volumetric part and store them
345 auto stress = computeDeviatoricVolumetricSum(stressDeviator, volumetricStress);
346
347 status->letTempStressVectorBe(stress);
348
349 // compute and update plastic strain and q
350 status->letTempPlasticStrainBe(plasticStrain);
351}
352
353void
354DustMaterial :: performF1return(double i1, double rho, GaussPoint *gp) const
355{
356 auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
357 double bulkModulus = status->giveBulkModulus();
358 double shearModulus = status->giveShearModulus();
359 double q = status->giveQ();
360 double tempQ = status->giveTempQ();
361 double m = 9 * bulkModulus / ( 2 * shearModulus );
362 int positiveFlag = 0;
363
364 for ( int i = 0; i < newtonIter; i++ ) {
365 double vfI1 = functionI1(q, tempQ, i1, bulkModulus);
366 double vfI1DQ = functionI1DQ(tempQ, bulkModulus);
367 double a = ( vfI1 - tempQ ) / ( ft - tempQ );
368 double b = functionFeDI1(vfI1);
369 double c = rho - functionFe(vfI1);
370 double da = ( ( vfI1DQ - 1 ) * ( ft - tempQ ) + ( vfI1 - tempQ ) ) / ( ( ft - tempQ ) * ( ft - tempQ ) );
371 double db = functionFeDI1DI1(vfI1) * vfI1DQ;
372 double dc = -functionFeDI1(vfI1) * vfI1DQ;
373 double d = da * b * c + a * db * c + a * b * dc;
374 double fx = -3 *bulkModulus *functionH(q, tempQ) - m * a * b * c;
375 double dfx = -3 *bulkModulus *functionHDQ(tempQ) - m * d;
376 tempQ -= fx / dfx;
377 if ( tempQ >= 0 ) {
378 if ( positiveFlag >= 1 ) {
379 status->letTempQBe(0.0);
380 return;
381 }
382
383 tempQ = 0;
384 positiveFlag += 1;
385 }
386
387 if ( fabs(fx / dfx / tempQ) < newtonTol ) {
388 status->letTempQBe(tempQ);
389 return;
390 }
391 }
392
393 OOFEM_LOG_DEBUG(" i1 %e rho %e bulkM %e shearM %e\n", i1, rho, bulkModulus, shearModulus);
394 OOFEM_ERROR("Newton's method did not converge");
395}
396
397void
398DustMaterial :: performF2return(double i1, double rho, GaussPoint *gp) const
399{
400 auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
401 double bulkModulus = status->giveBulkModulus();
402 double shearModulus = status->giveShearModulus();
403 double q = status->giveQ();
404 double qRight = q;
405 double qLeft = q;
406 double tempQ = .5 * ( qLeft + qRight );
407 for ( int i = 0; i < newtonIter; i++ ) {
408 double fx = i1 - 3 *bulkModulus *functionH(q, qLeft) - qLeft;
409 double dfx = -3 *bulkModulus *functionHDQ(qLeft) - 1;
410 qLeft -= fx / dfx;
411 if ( fabs(fx / dfx / q0) < newtonTol ) {
412 break;
413 }
414 }
415
416 for ( int i = 0; i < newtonIter; i++ ) {
417 double fq = fTempR2(tempQ, q, i1, rho, bulkModulus, shearModulus);
418 if ( fabs( ( qRight - qLeft ) / qRight ) < newtonTol ) {
419 status->letTempQBe(tempQ);
420 return;
421 }
422
423 if ( fq > 0 ) {
424 qRight = tempQ;
425 } else {
426 qLeft = tempQ;
427 }
428
429 tempQ = .5 * ( qLeft + qRight );
430 }
431
432 OOFEM_ERROR("bisection method did not converge");
433}
434
435void
436DustMaterial :: computeQFromPlastVolEps(double &answer, double q, double deltaVolumetricPlasticStrain) const
437{
438 if ( q >= 0. ) {
439 answer = 0.;
440 return;
441 }
442
443 for ( int i = 0; i <= newtonIter; i++ ) {
444 double fx = functionH(q, answer) - deltaVolumetricPlasticStrain;
445 double dfx = functionHDQ(answer);
446 answer -= fx / dfx;
447 if ( fabs(fx / dfx / answer) < newtonTol ) {
448 if ( answer > 0 ) {
449 answer = 0.;
450 }
451
452 return;
453 }
454 }
455
456 OOFEM_LOG_DEBUG(" dVolEpsPl: %e\n", deltaVolumetricPlasticStrain);
457 OOFEM_ERROR("Newton's method did not converge");
458}
459
461DustMaterial :: give3dMaterialStiffnessMatrix(MatResponseMode mode,
462 GaussPoint *gp,
463 TimeStep *tStep) const
464{
465 auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
466 double ym0 = LEMaterial.giveYoungsModulus();
467 double ym = status->giveYoungsModulus();
468 double coeff = status->giveVolumetricPlasticStrain() < 0 ? ym / ym0 : 1.0;
469 if ( mode == ElasticStiffness ) {
470 return LEMaterial.give3dMaterialStiffnessMatrix(mode, gp, tStep);
471 } else if ( mode == SecantStiffness || mode == TangentStiffness ) {
472 return coeff * LEMaterial.give3dMaterialStiffnessMatrix(mode, gp, tStep);
473 } else {
474 OOFEM_ERROR("Unsupported MatResponseMode");
475 }
476}
477
478int
479DustMaterial :: setIPValue(const FloatArray &value, GaussPoint *gp, InternalStateType type)
480{
481 auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
482 if ( type == IST_PlasticStrainTensor ) {
483 status->letPlasticStrainBe(value);
484 return 1;
485 } else if ( type == IST_StressCapPos ) {
486 status->letQBe( value.at(1) );
487 return 1;
488 } else {
489 return StructuralMaterial :: setIPValue(value, gp, type);
490 }
491}
492
493int
494DustMaterial :: giveIPValue(FloatArray &answer,
495 GaussPoint *gp,
497 TimeStep *tStep)
498{
499 const auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
500 if ( type == IST_PlasticStrainTensor ) {
501 answer = status->givePlasticStrain();
502 return 1;
503 } else if ( type == IST_PrincipalPlasticStrainTensor ) {
504 computePrincipalValues(answer, status->givePlasticStrain(), principal_strain);
505 return 1;
506 } else if ( type == IST_VolumetricPlasticStrain ) {
507 answer.resize(1);
508 answer.at(1) = status->giveVolumetricPlasticStrain();
509 return 1;
510 } else if ( type == IST_StressCapPos ) {
511 answer.resize(1);
512 answer.at(1) = status->giveQ();
513 return 1;
514 } else {
515 return StructuralMaterial :: giveIPValue(answer, gp, type, tStep);
516 }
517
518 // return 0;
519}
520
521std::unique_ptr<MaterialStatus>
522DustMaterial :: CreateStatus(GaussPoint *gp) const
523{
524 return std::make_unique<DustMaterialStatus>(gp, this->giveQ0() );
525}
526
527double
528DustMaterial :: functionFe(double i1) const
529{
530 return alpha - lambda *exp(beta *i1) - theta * i1;
531}
532
533double
534DustMaterial :: functionFeDI1(double i1) const
535{
536 return -lambda *beta *exp(beta *i1) - theta;
537}
538
539double
540DustMaterial :: functionFeDI1DI1(double i1) const
541{
542 return -lambda *beta *beta *exp(beta *i1);
543}
544
545double
546DustMaterial :: functionFc(double rho, double i1, double q) const
547{
548 return sqrt( rho * rho + 1 / rEll / rEll * ( q - i1 ) * ( q - i1 ) );
549}
550
551double
552DustMaterial :: yieldFunction1(double rho, double i1) const
553{
554 return rho - functionFe(i1);
555}
556
557double
558DustMaterial :: yieldFunction2(double rho, double i1, double q) const
559{
560 return functionFc(rho, i1, q) - functionFe(q);
561}
562
563double
564DustMaterial :: yieldFunction3(double i1) const
565{
566 return i1 - ft;
567}
568
569double
570DustMaterial :: functionX(double q) const
571{
572 return q - rEll * ( alpha - lambda * exp(beta * q) - theta * q );
573}
574
575double
576DustMaterial :: functionXDQ(double q) const
577{
578 return 1 - rEll * ( -lambda * beta * exp(beta * q) - theta );
579}
580
581void
582DustMaterial :: solveQ0(double &answer) const
583{
584 for ( int i = 0; i < newtonIter; i++ ) {
585 double fx = -x0 + answer - rEll * ( alpha - lambda * exp(beta * answer) - theta * answer );
586 double dfx = 1 - rEll * ( -beta * lambda * exp(beta * answer) - theta );
587 answer -= fx / dfx;
588 if ( fabs(fx / dfx / answer) < newtonTol ) {
589 if ( answer >= 0 ) {
590 OOFEM_ERROR("internal parameter q has to be negative");
591 }
592
593 return;
594 }
595 }
596
597 OOFEM_ERROR("Newton's method did not converge");
598}
599
600void
601DustMaterial :: computeAndSetBulkAndShearModuli(double &bulkModulus, double &shearModulus, GaussPoint *gp) const
602{
603 auto status = static_cast< DustMaterialStatus * >( giveStatus(gp) );
604 double ym = LEMaterial.giveYoungsModulus();
605 double nu = LEMaterial.givePoissonsRatio();
606 double volumetricPlasticStrain = status->giveVolumetricPlasticStrain();
607 if ( volumetricPlasticStrain < 0. ) {
608 ym -= mStiff * volumetricPlasticStrain;
609 }
610
611 bulkModulus = IsotropicLinearElasticMaterial :: computeBulkModulusFromYoungAndPoisson(ym, nu);
612 shearModulus = IsotropicLinearElasticMaterial :: computeShearModulusFromYoungAndPoisson(ym, nu);
613 status->setBulkModulus(bulkModulus);
614 status->setShearModulus(shearModulus);
615 status->setYoungsModulus(ym);
616}
617
619DustMaterial :: computePlastStrainDirM1(const FloatArrayF<6> &stressDeviator, double rho, double i1, double q) const
620{
621 double temp = ( lambda * beta * exp(beta * i1) + theta ) * ( i1 - q ) / ( ft - q );
622
623 return computeDeviatoricVolumetricSum((1./rho) * stressDeviator, temp);
624}
625
627DustMaterial :: computePlastStrainDirM2(const FloatArrayF<6> &stressDeviator, double rho, double i1, double q) const
628{
629 double fc = functionFc(rho, i1, q);
630 double temp = ( q - i1 ) / ( rEll * rEll * fc );
631
632 return computeDeviatoricVolumetricSum((1./fc) * stressDeviator, -temp);
633}
634
636DustMaterial :: computePlastStrainDirM3(const FloatArrayF<6> &stressDeviator, double rho, double i1, double q) const
637{
638 double feft = functionFe(ft);
639 double dfeft = functionFeDI1(ft);
640 double temp = 1 - ( 1 + dfeft ) * rho / feft;
641
642 return computeDeviatoricVolumetricSum((1./feft) * stressDeviator, temp);
643}
644
645double
646DustMaterial :: functionH(double q, double tempQ) const
647{
648 double xq = functionX(q);
649 double xtq = functionX(tempQ);
650 switch ( hardeningType ) {
651 case 1:
652 return wHard * ( exp(dHard * xtq) - exp(dHard * xq) );
653
654 default: // 0
655 return dHard * wHard * ( xtq / ( 1 - dHard * xtq ) - xq / ( 1 - dHard * xq ) );
656 }
657}
658
659double
660DustMaterial :: functionHDQ(double tempQ) const
661{
662 double xtq = functionX(tempQ);
663 double dxtq = functionXDQ(tempQ);
664 switch ( hardeningType ) {
665 case 1:
666 return wHard *dHard *exp(dHard *xtq) * dHard * dxtq;
667
668 default: // 0
669 return dHard * wHard * ( dxtq * ( 1 - dHard * xtq ) - xtq * ( -dHard * dxtq ) ) / ( 1 - dHard * xtq ) / ( 1 - dHard * xtq );
670 }
671}
672
673double
674DustMaterial :: functionI1(double q, double tempQ, double i1, double bulkModulus) const
675{
676 return i1 - 3 *bulkModulus *functionH(q, tempQ);
677}
678
679double
680DustMaterial :: functionI1DQ(double tempQ, double bulkModulus) const
681{
682 return -3 *bulkModulus *functionHDQ(tempQ);
683}
684
685double
686DustMaterial :: computeDeltaGamma2(double tempQ, double q, double i1, double bulkModulus) const
687{
688 double vfH = functionH(q, tempQ);
689 return rEll *rEll *functionFe(tempQ) * vfH / ( 3 * ( i1 - 3 * bulkModulus * vfH - tempQ ) );
690}
691
692double
693DustMaterial :: computeDeltaGamma2DQ(double tempQ, double q, double i1, double bulkModulus) const
694{
695 double vfH = functionH(q, tempQ);
696 double vdfH = functionHDQ(tempQ);
697 double vfEq = functionFe(tempQ);
698 double vdfEq = functionFeDI1(tempQ);
699 double frac1 = rEll * rEll * vfEq * vfH;
700 double dfrac1 = rEll * rEll * ( vdfEq * vfH + vfEq * vdfH );
701 double frac2 = 3 * ( i1 - 3 * bulkModulus * vfH - tempQ );
702 double dfrac2 = 3 * ( -3 * bulkModulus * vdfH - 1 );
703 return ( dfrac1 * frac2 - frac1 * dfrac2 ) / frac2 / frac2;
704}
705
706double
707DustMaterial :: fTempR2(double tempQ, double q, double i1, double rho, double bulkModulus, double shearModulus) const
708{
709 double vfEq = functionFe(tempQ);
710 double dgq = computeDeltaGamma2(tempQ, q, i1, bulkModulus);
711 double frac = ( vfEq + 2 * shearModulus * dgq );
712 double a = rho * vfEq / frac;
713 frac = ( rEll * rEll * vfEq + 9 * bulkModulus * dgq );
714 double b = ( tempQ - i1 ) * rEll * vfEq / frac;
715 return a * a + b * b - vfEq * vfEq;
716}
717} // end namespace oofem
#define REGISTER_Material(class)
FloatArrayF< 6 > plasticStrain
Plastic strain.
Definition dustmat.h:82
const FloatArrayF< 6 > & givePlasticStrain() const
Definition dustmat.h:117
double q
Hardening parameter q.
Definition dustmat.h:86
double giveBulkModulus() const
Definition dustmat.h:196
FloatArrayF< 6 > tempPlasticStrain
Definition dustmat.h:83
int stateFlag
Indicates the state (i.e. elastic, yielding, unloading) of the Gauss point.
Definition dustmat.h:97
void solveQ0(double &answer) const
Definition dustmat.C:582
double functionFe(double i1) const
Definition dustmat.C:528
double newtonTol
Tollerance for iterative methods.
Definition dustmat.h:261
double yieldFunction2(double rho, double i1, double q) const
Definition dustmat.C:558
double x0
Parameter determining shape of yield surface (param X0 in original publication).
Definition dustmat.h:253
double functionI1DQ(double tempQ, double bulkModulus) const
Definition dustmat.C:680
double giveQ0() const
Definition dustmat.h:472
double functionX(double q) const
Definition dustmat.C:570
double computeDeltaGamma2(double tempQ, double q, double i1, double bulkModulus) const
Definition dustmat.C:686
double yieldFunction1(double rho, double i1) const
Definition dustmat.C:552
double dHard
Parameter determining hardening law (parameter D in original publication).
Definition dustmat.h:259
int hardeningType
Parameter determining hardening type.
Definition dustmat.h:249
double alpha
Parameter determining shape of yield surface.
Definition dustmat.h:237
FloatArrayF< 6 > computePlastStrainDirM1(const FloatArrayF< 6 > &stressDeviator, double rho, double i1, double q) const
Definition dustmat.C:619
void performStressReturn(GaussPoint *gp, const FloatArrayF< 6 > &strain) const
Definition dustmat.C:243
void performF2return(double i1, double rho, GaussPoint *gp) const
Definition dustmat.C:398
double theta
Parameter determining shape of yield surface.
Definition dustmat.h:243
double q0
Parameter determining shape of yield surface.
Definition dustmat.h:255
double functionHDQ(double tempQ) const
Definition dustmat.C:660
double beta
Parameter determining shape of yield surface.
Definition dustmat.h:239
double wHard
Parameter determining hardening law (parameter W in original publication).
Definition dustmat.h:257
double rEll
Parameter determining shape of yield surface (param R in original publication).
Definition dustmat.h:247
double functionH(double q, double tempQ) const
Definition dustmat.C:646
double functionI1(double q, double tempQ, double i1, double bulkModulus) const
Definition dustmat.C:674
void computeQFromPlastVolEps(double &answer, double q, double deltaVolumetricPlasticStrain) const
Definition dustmat.C:436
double functionFeDI1(double i1) const
Definition dustmat.C:534
int newtonIter
Maximum number of iterations for iterative methods.
Definition dustmat.h:263
double fTempR2(double tempQ, double q, double i1, double rho, double bulkModulus, double shearModulus) const
Definition dustmat.C:707
double mStiff
Parameter increasing stiffness (parameter M in original publication).
Definition dustmat.h:251
IsotropicLinearElasticMaterial LEMaterial
Pointer for linear elastic material.
Definition dustmat.h:234
double lambda
Parameter determining shape of yield surface.
Definition dustmat.h:241
double ft
Parameter determining shape of yield surface (param T in original publication).
Definition dustmat.h:245
FloatArrayF< 6 > computePlastStrainDirM2(const FloatArrayF< 6 > &stressDeviator, double rho, double i1, double q) const
Definition dustmat.C:627
double functionXDQ(double q) const
Definition dustmat.C:576
FloatArrayF< 6 > computePlastStrainDirM3(const FloatArrayF< 6 > &stressDeviator, double rho, double i1, double q) const
Definition dustmat.C:636
double functionFc(double rho, double i1, double q) const
Definition dustmat.C:546
void computeAndSetBulkAndShearModuli(double &bulkModulus, double &shearModulus, GaussPoint *gp) const
Definition dustmat.C:601
double yieldFunction3(double i1) const
Definition dustmat.C:564
void performF1return(double i1, double rho, GaussPoint *gp) const
Definition dustmat.C:354
double functionFeDI1DI1(double i1) const
Definition dustmat.C:540
void resize(Index s)
Definition floatarray.C:94
double & at(Index i)
Definition floatarray.h:202
GaussPoint * gp
Associated integration point.
virtual MaterialStatus * giveStatus(GaussPoint *gp) const
Definition material.C:206
virtual void initTempStatus(GaussPoint *gp) const
Definition material.C:221
StructuralMaterialStatus(GaussPoint *g)
Constructor. Creates new StructuralMaterialStatus with IntegrationPoint g.
FloatArray tempStrainVector
Temporary strain vector in reduced form (to find balanced state).
FloatArray tempStressVector
Temporary stress vector in reduced form (increments are used mainly in nonlinear analysis).
FloatArray stressVector
Equilibrated stress vector in reduced form.
FloatArray strainVector
Equilibrated strain vector in reduced form.
static FloatArrayF< 6 > computeDeviatoricVolumetricSum(const FloatArrayF< 6 > &dev, double mean)
static void computePrincipalValues(FloatArray &answer, const FloatArray &s, stressStrainPrincMode mode)
Common functions for convenience.
StructuralMaterial(int n, Domain *d)
static double computeSecondCoordinate(const FloatArrayF< 6 > &s)
static std::pair< FloatArrayF< 6 >, double > computeDeviatoricVolumetricSplit(const FloatArrayF< 6 > &s)
FloatArrayF< 6 > computeStressIndependentStrainVector_3d(GaussPoint *gp, TimeStep *tStep, ValueModeType mode) const
#define _IFT_DustMaterial_rEll
Definition dustmat.h:54
#define _IFT_DustMaterial_newtonTol
Definition dustmat.h:56
#define _IFT_DustMaterial_ft
Definition dustmat.h:51
#define _IFT_DustMaterial_dHard
Definition dustmat.h:59
#define _IFT_DustMaterial_newtonIter
Definition dustmat.h:57
#define _IFT_DustMaterial_lambda
Definition dustmat.h:49
#define _IFT_DustMaterial_hardeningType
Definition dustmat.h:52
#define _IFT_DustMaterial_x0
Definition dustmat.h:55
#define _IFT_DustMaterial_mStiff
Definition dustmat.h:53
#define _IFT_DustMaterial_wHard
Definition dustmat.h:58
#define _IFT_DustMaterial_beta
Definition dustmat.h:48
#define _IFT_DustMaterial_theta
Definition dustmat.h:50
#define _IFT_DustMaterial_alpha
Definition dustmat.h:47
#define OOFEM_ERROR(...)
Definition error.h:79
#define IR_GIVE_OPTIONAL_FIELD(__ir, __value, __id)
Definition inputrecord.h:75
#define OOFEM_LOG_DEBUG(...)
Definition logger.h:144
long ContextMode
Definition contextmode.h:43
@ principal_strain
For computing principal strains from engineering strains.

This page is part of the OOFEM-3.0 documentation. Copyright Copyright (C) 1994-2025 Borek Patzak Bořek Patzák
Project e-mail: oofem@fsv.cvut.cz
Generated at for OOFEM by doxygen 1.15.0 written by Dimitri van Heesch, © 1997-2011