Merge branch 'development' of magit1.mpie.de:damask/DAMASK into development

This commit is contained in:
Martin Diehl 2018-02-21 07:53:00 +01:00
commit 051f3592ea
41 changed files with 2990 additions and 1278 deletions

@ -1 +1 @@
Subproject commit 17d61f88ce2d386d40b45a002d43556bfbb27340 Subproject commit 8de4f792a46d98d98418dbf2d3e621b22c13b18a

View File

@ -1 +1 @@
v2.0.1-1073-gc544fa1 v2.0.1-1082-g8d81e12

View File

@ -0,0 +1,7 @@
elasticity hooke
c11 160.0e9
c12 90.0e9
c13 66.0e9
c33 181.7e9
c44 46.5e9

View File

@ -0,0 +1,11 @@
elasticity hooke
c11 100.0e9
c22 100.0e9
c33 100.0e9
c12 0.0e9
c13 0.0e9
c23 0.0e9
c44 50.0e9
c55 50.0e9
c66 50.0e9

View File

@ -0,0 +1,4 @@
elasticity hooke
c11 100.0e9
c12 0.0e9

View File

@ -0,0 +1,3 @@
reference_temperature 300.0
specific_heat 1
mass_density 1

View File

@ -0,0 +1,8 @@
(kinematics) thermal_expansion
thermal_expansion11 9.5e-6
thermal_expansion22 9.5e-6
thermal_expansion33 5.6e-6
(source) thermal_externalheat
externalheat_time 0 500 500.001 1000 # 500 secs supplying 1 Watt, then removing 1 Watt
externalheat_rate 1 1 -1 -1

View File

@ -0,0 +1,9 @@
(kinematics) thermal_expansion
thermal_expansion11 5e-6
thermal_expansion22 10e-6
thermal_expansion33 20e-6
lattice_structure orthorhombic
(source) thermal_externalheat
externalheat_time 0 500 500.001 1000 # 500 secs supplying 1 Watt, then removing 1 Watt
externalheat_rate 1 1 -1 -1

View File

@ -0,0 +1,6 @@
(kinematics) thermal_expansion
thermal_expansion11 10e-6
(source) thermal_externalheat
externalheat_time 0 500 500.001 1000 # 500 secs supplying 1 Watt, then removing 1 Watt
externalheat_rate 1 1 -1 -1

View File

@ -0,0 +1,427 @@
9 header
geom_addPrimitive v2.0.1-1073-gc544fa1 -c 32 32 32 -d -16 -16 -16 inclusion.geom
geom_canvas v2.0.1-1073-gc544fa1 -o 16 16 16 -g 32 32 32
geom_translate v2.0.1-1073-gc544fa1 -s 1,2,2,6 Ti_Ti.geom
geom_pack v2.0.1-1073-gc544fa1 Ti_Ti.geom isotropic_anisotropic.geom isotropic_isotropic.geom isotropic_rotated.geom
grid a 32 b 32 c 32
size x 0.5 y 0.5 z 0.5
origin x 0.25 y 0.25 z 0.25
homogenization 1
microstructures 2
8623 of 2
2 of 6
29 of 2
4 of 6
27 of 2
6 of 6
26 of 2
6 of 6
27 of 2
4 of 6
29 of 2
2 of 6
798 of 2
2 of 6
28 of 2
6 of 6
25 of 2
8 of 6
24 of 2
8 of 6
23 of 2
10 of 6
22 of 2
10 of 6
23 of 2
8 of 6
24 of 2
8 of 6
25 of 2
6 of 6
28 of 2
2 of 6
701 of 2
4 of 6
26 of 2
8 of 6
23 of 2
10 of 6
22 of 2
10 of 6
21 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
21 of 2
10 of 6
22 of 2
10 of 6
23 of 2
8 of 6
26 of 2
4 of 6
637 of 2
2 of 6
27 of 2
8 of 6
23 of 2
10 of 6
21 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
21 of 2
10 of 6
23 of 2
8 of 6
27 of 2
2 of 6
604 of 2
6 of 6
24 of 2
10 of 6
21 of 2
12 of 6
20 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
20 of 2
12 of 6
21 of 2
10 of 6
24 of 2
6 of 6
572 of 2
2 of 6
27 of 2
8 of 6
23 of 2
10 of 6
21 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
17 of 2
16 of 6
16 of 2
16 of 6
17 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
21 of 2
10 of 6
23 of 2
8 of 6
27 of 2
2 of 6
541 of 2
4 of 6
26 of 2
8 of 6
22 of 2
12 of 6
20 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
17 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
17 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
20 of 2
12 of 6
22 of 2
8 of 6
26 of 2
4 of 6
539 of 2
6 of 6
24 of 2
10 of 6
21 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
17 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
17 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
21 of 2
10 of 6
24 of 2
6 of 6
538 of 2
6 of 6
24 of 2
10 of 6
21 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
17 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
17 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
21 of 2
10 of 6
24 of 2
6 of 6
539 of 2
4 of 6
26 of 2
8 of 6
22 of 2
12 of 6
20 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
17 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
16 of 2
16 of 6
17 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
20 of 2
12 of 6
22 of 2
8 of 6
26 of 2
4 of 6
541 of 2
2 of 6
27 of 2
8 of 6
23 of 2
10 of 6
21 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
17 of 2
16 of 6
16 of 2
16 of 6
17 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
21 of 2
10 of 6
23 of 2
8 of 6
27 of 2
2 of 6
572 of 2
6 of 6
24 of 2
10 of 6
21 of 2
12 of 6
20 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
20 of 2
12 of 6
21 of 2
10 of 6
24 of 2
6 of 6
604 of 2
2 of 6
27 of 2
8 of 6
23 of 2
10 of 6
21 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
19 of 2
14 of 6
18 of 2
14 of 6
19 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
21 of 2
10 of 6
23 of 2
8 of 6
27 of 2
2 of 6
637 of 2
4 of 6
26 of 2
8 of 6
23 of 2
10 of 6
22 of 2
10 of 6
21 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
20 of 2
12 of 6
21 of 2
10 of 6
22 of 2
10 of 6
23 of 2
8 of 6
26 of 2
4 of 6
701 of 2
2 of 6
28 of 2
6 of 6
25 of 2
8 of 6
24 of 2
8 of 6
23 of 2
10 of 6
22 of 2
10 of 6
23 of 2
8 of 6
24 of 2
8 of 6
25 of 2
6 of 6
28 of 2
2 of 6
798 of 2
2 of 6
29 of 2
4 of 6
27 of 2
6 of 6
26 of 2
6 of 6
27 of 2
4 of 6
29 of 2
2 of 6
8623 of 2

View File

@ -0,0 +1,427 @@
9 header
geom_addPrimitive v2.0.1-1073-gc544fa1 -c 32 32 32 -d -16 -16 -16 inclusion.geom
geom_canvas v2.0.1-1073-gc544fa1 -o 16 16 16 -g 32 32 32
geom_translate v2.0.1-1073-gc544fa1 -s 2,4 isotropic_anisotropic.geom
geom_pack v2.0.1-1073-gc544fa1 Ti_Ti.geom isotropic_anisotropic.geom isotropic_isotropic.geom isotropic_rotated.geom
grid a 32 b 32 c 32
size x 0.5 y 0.5 z 0.5
origin x 0.25 y 0.25 z 0.25
homogenization 1
microstructures 2
8623 of 1
2 of 4
29 of 1
4 of 4
27 of 1
6 of 4
26 of 1
6 of 4
27 of 1
4 of 4
29 of 1
2 of 4
798 of 1
2 of 4
28 of 1
6 of 4
25 of 1
8 of 4
24 of 1
8 of 4
23 of 1
10 of 4
22 of 1
10 of 4
23 of 1
8 of 4
24 of 1
8 of 4
25 of 1
6 of 4
28 of 1
2 of 4
701 of 1
4 of 4
26 of 1
8 of 4
23 of 1
10 of 4
22 of 1
10 of 4
21 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
21 of 1
10 of 4
22 of 1
10 of 4
23 of 1
8 of 4
26 of 1
4 of 4
637 of 1
2 of 4
27 of 1
8 of 4
23 of 1
10 of 4
21 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
21 of 1
10 of 4
23 of 1
8 of 4
27 of 1
2 of 4
604 of 1
6 of 4
24 of 1
10 of 4
21 of 1
12 of 4
20 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
20 of 1
12 of 4
21 of 1
10 of 4
24 of 1
6 of 4
572 of 1
2 of 4
27 of 1
8 of 4
23 of 1
10 of 4
21 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
17 of 1
16 of 4
16 of 1
16 of 4
17 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
21 of 1
10 of 4
23 of 1
8 of 4
27 of 1
2 of 4
541 of 1
4 of 4
26 of 1
8 of 4
22 of 1
12 of 4
20 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
17 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
17 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
20 of 1
12 of 4
22 of 1
8 of 4
26 of 1
4 of 4
539 of 1
6 of 4
24 of 1
10 of 4
21 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
17 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
17 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
21 of 1
10 of 4
24 of 1
6 of 4
538 of 1
6 of 4
24 of 1
10 of 4
21 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
17 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
17 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
21 of 1
10 of 4
24 of 1
6 of 4
539 of 1
4 of 4
26 of 1
8 of 4
22 of 1
12 of 4
20 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
17 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
16 of 1
16 of 4
17 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
20 of 1
12 of 4
22 of 1
8 of 4
26 of 1
4 of 4
541 of 1
2 of 4
27 of 1
8 of 4
23 of 1
10 of 4
21 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
17 of 1
16 of 4
16 of 1
16 of 4
17 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
21 of 1
10 of 4
23 of 1
8 of 4
27 of 1
2 of 4
572 of 1
6 of 4
24 of 1
10 of 4
21 of 1
12 of 4
20 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
20 of 1
12 of 4
21 of 1
10 of 4
24 of 1
6 of 4
604 of 1
2 of 4
27 of 1
8 of 4
23 of 1
10 of 4
21 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
19 of 1
14 of 4
18 of 1
14 of 4
19 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
21 of 1
10 of 4
23 of 1
8 of 4
27 of 1
2 of 4
637 of 1
4 of 4
26 of 1
8 of 4
23 of 1
10 of 4
22 of 1
10 of 4
21 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
20 of 1
12 of 4
21 of 1
10 of 4
22 of 1
10 of 4
23 of 1
8 of 4
26 of 1
4 of 4
701 of 1
2 of 4
28 of 1
6 of 4
25 of 1
8 of 4
24 of 1
8 of 4
23 of 1
10 of 4
22 of 1
10 of 4
23 of 1
8 of 4
24 of 1
8 of 4
25 of 1
6 of 4
28 of 1
2 of 4
798 of 1
2 of 4
29 of 1
4 of 4
27 of 1
6 of 4
26 of 1
6 of 4
27 of 1
4 of 4
29 of 1
2 of 4
8623 of 1

View File

@ -0,0 +1,427 @@
9 header
geom_addPrimitive v2.0.1-1073-gc544fa1 -c 32 32 32 -d -16 -16 -16 inclusion.geom
geom_canvas v2.0.1-1073-gc544fa1 -o 16 16 16 -g 32 32 32
geom_translate v2.0.1-1073-gc544fa1 -s 2,3 isotropic_isotropic.geom
geom_pack v2.0.1-1073-gc544fa1 Ti_Ti.geom isotropic_anisotropic.geom isotropic_isotropic.geom isotropic_rotated.geom
grid a 32 b 32 c 32
size x 0.5 y 0.5 z 0.5
origin x 0.25 y 0.25 z 0.25
homogenization 1
microstructures 2
8623 of 1
2 of 3
29 of 1
4 of 3
27 of 1
6 of 3
26 of 1
6 of 3
27 of 1
4 of 3
29 of 1
2 of 3
798 of 1
2 of 3
28 of 1
6 of 3
25 of 1
8 of 3
24 of 1
8 of 3
23 of 1
10 of 3
22 of 1
10 of 3
23 of 1
8 of 3
24 of 1
8 of 3
25 of 1
6 of 3
28 of 1
2 of 3
701 of 1
4 of 3
26 of 1
8 of 3
23 of 1
10 of 3
22 of 1
10 of 3
21 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
21 of 1
10 of 3
22 of 1
10 of 3
23 of 1
8 of 3
26 of 1
4 of 3
637 of 1
2 of 3
27 of 1
8 of 3
23 of 1
10 of 3
21 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
21 of 1
10 of 3
23 of 1
8 of 3
27 of 1
2 of 3
604 of 1
6 of 3
24 of 1
10 of 3
21 of 1
12 of 3
20 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
20 of 1
12 of 3
21 of 1
10 of 3
24 of 1
6 of 3
572 of 1
2 of 3
27 of 1
8 of 3
23 of 1
10 of 3
21 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
17 of 1
16 of 3
16 of 1
16 of 3
17 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
21 of 1
10 of 3
23 of 1
8 of 3
27 of 1
2 of 3
541 of 1
4 of 3
26 of 1
8 of 3
22 of 1
12 of 3
20 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
17 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
17 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
20 of 1
12 of 3
22 of 1
8 of 3
26 of 1
4 of 3
539 of 1
6 of 3
24 of 1
10 of 3
21 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
17 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
17 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
21 of 1
10 of 3
24 of 1
6 of 3
538 of 1
6 of 3
24 of 1
10 of 3
21 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
17 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
17 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
21 of 1
10 of 3
24 of 1
6 of 3
539 of 1
4 of 3
26 of 1
8 of 3
22 of 1
12 of 3
20 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
17 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
16 of 1
16 of 3
17 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
20 of 1
12 of 3
22 of 1
8 of 3
26 of 1
4 of 3
541 of 1
2 of 3
27 of 1
8 of 3
23 of 1
10 of 3
21 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
17 of 1
16 of 3
16 of 1
16 of 3
17 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
21 of 1
10 of 3
23 of 1
8 of 3
27 of 1
2 of 3
572 of 1
6 of 3
24 of 1
10 of 3
21 of 1
12 of 3
20 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
20 of 1
12 of 3
21 of 1
10 of 3
24 of 1
6 of 3
604 of 1
2 of 3
27 of 1
8 of 3
23 of 1
10 of 3
21 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
19 of 1
14 of 3
18 of 1
14 of 3
19 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
21 of 1
10 of 3
23 of 1
8 of 3
27 of 1
2 of 3
637 of 1
4 of 3
26 of 1
8 of 3
23 of 1
10 of 3
22 of 1
10 of 3
21 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
20 of 1
12 of 3
21 of 1
10 of 3
22 of 1
10 of 3
23 of 1
8 of 3
26 of 1
4 of 3
701 of 1
2 of 3
28 of 1
6 of 3
25 of 1
8 of 3
24 of 1
8 of 3
23 of 1
10 of 3
22 of 1
10 of 3
23 of 1
8 of 3
24 of 1
8 of 3
25 of 1
6 of 3
28 of 1
2 of 3
798 of 1
2 of 3
29 of 1
4 of 3
27 of 1
6 of 3
26 of 1
6 of 3
27 of 1
4 of 3
29 of 1
2 of 3
8623 of 1

View File

@ -0,0 +1,427 @@
9 header
geom_addPrimitive v2.0.1-1073-gc544fa1 -c 32 32 32 -d -16 -16 -16 inclusion.geom
geom_canvas v2.0.1-1073-gc544fa1 -o 16 16 16 -g 32 32 32
geom_translate v2.0.1-1073-gc544fa1 -s 2,5 isotropic_rotated.geom
geom_pack v2.0.1-1073-gc544fa1 Ti_Ti.geom isotropic_anisotropic.geom isotropic_isotropic.geom isotropic_rotated.geom
grid a 32 b 32 c 32
size x 0.5 y 0.5 z 0.5
origin x 0.25 y 0.25 z 0.25
homogenization 1
microstructures 2
8623 of 1
2 of 5
29 of 1
4 of 5
27 of 1
6 of 5
26 of 1
6 of 5
27 of 1
4 of 5
29 of 1
2 of 5
798 of 1
2 of 5
28 of 1
6 of 5
25 of 1
8 of 5
24 of 1
8 of 5
23 of 1
10 of 5
22 of 1
10 of 5
23 of 1
8 of 5
24 of 1
8 of 5
25 of 1
6 of 5
28 of 1
2 of 5
701 of 1
4 of 5
26 of 1
8 of 5
23 of 1
10 of 5
22 of 1
10 of 5
21 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
21 of 1
10 of 5
22 of 1
10 of 5
23 of 1
8 of 5
26 of 1
4 of 5
637 of 1
2 of 5
27 of 1
8 of 5
23 of 1
10 of 5
21 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
21 of 1
10 of 5
23 of 1
8 of 5
27 of 1
2 of 5
604 of 1
6 of 5
24 of 1
10 of 5
21 of 1
12 of 5
20 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
20 of 1
12 of 5
21 of 1
10 of 5
24 of 1
6 of 5
572 of 1
2 of 5
27 of 1
8 of 5
23 of 1
10 of 5
21 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
17 of 1
16 of 5
16 of 1
16 of 5
17 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
21 of 1
10 of 5
23 of 1
8 of 5
27 of 1
2 of 5
541 of 1
4 of 5
26 of 1
8 of 5
22 of 1
12 of 5
20 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
17 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
17 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
20 of 1
12 of 5
22 of 1
8 of 5
26 of 1
4 of 5
539 of 1
6 of 5
24 of 1
10 of 5
21 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
17 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
17 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
21 of 1
10 of 5
24 of 1
6 of 5
538 of 1
6 of 5
24 of 1
10 of 5
21 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
17 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
17 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
21 of 1
10 of 5
24 of 1
6 of 5
539 of 1
4 of 5
26 of 1
8 of 5
22 of 1
12 of 5
20 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
17 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
16 of 1
16 of 5
17 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
20 of 1
12 of 5
22 of 1
8 of 5
26 of 1
4 of 5
541 of 1
2 of 5
27 of 1
8 of 5
23 of 1
10 of 5
21 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
17 of 1
16 of 5
16 of 1
16 of 5
17 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
21 of 1
10 of 5
23 of 1
8 of 5
27 of 1
2 of 5
572 of 1
6 of 5
24 of 1
10 of 5
21 of 1
12 of 5
20 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
20 of 1
12 of 5
21 of 1
10 of 5
24 of 1
6 of 5
604 of 1
2 of 5
27 of 1
8 of 5
23 of 1
10 of 5
21 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
19 of 1
14 of 5
18 of 1
14 of 5
19 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
21 of 1
10 of 5
23 of 1
8 of 5
27 of 1
2 of 5
637 of 1
4 of 5
26 of 1
8 of 5
23 of 1
10 of 5
22 of 1
10 of 5
21 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
20 of 1
12 of 5
21 of 1
10 of 5
22 of 1
10 of 5
23 of 1
8 of 5
26 of 1
4 of 5
701 of 1
2 of 5
28 of 1
6 of 5
25 of 1
8 of 5
24 of 1
8 of 5
23 of 1
10 of 5
22 of 1
10 of 5
23 of 1
8 of 5
24 of 1
8 of 5
25 of 1
6 of 5
28 of 1
2 of 5
798 of 1
2 of 5
29 of 1
4 of 5
27 of 1
6 of 5
26 of 1
6 of 5
27 of 1
4 of 5
29 of 1
2 of 5
8623 of 1

View File

@ -0,0 +1,111 @@
#-------------------#
<homogenization>
#-------------------#
[direct]
type none # isostrain 1 grain
thermal adiabatic # thermal strain (stress) induced mass transport
initialT 300.0
(output) temperature
#-------------------#
<crystallite>
#-------------------#
[aLittleSomething]
(output) texture
(output) f
(output) p
(output) fe
(output) fi
(output) fp
#-------------------#
<phase>
#-------------------#
#.................
[isotropic matrix]
lattice_structure isotropic
plasticity none
{config/elastic_isotropic.config}
{config/thermal.config}
#.................
[Ti matrix]
lattice_structure hex
covera_ratio 1.587
plasticity none
{config/elastic_Ti.config}
{config/thermal.config}
#.................
[isotropic inclusion]
lattice_structure isotropic
plasticity none
{config/elastic_isotropic.config}
{config/thermal.config}
{config/thermalExpansion_isotropic.config}
#.................
[anisotropic inclusion]
lattice_structure orthorhombic
plasticity none
{config/elastic_fullyAnisotropic.config}
{config/thermal.config}
{config/thermalExpansion_fullyAnisotropic.config}
#.................
[Ti inclusion]
lattice_structure hex
covera_ratio 1.587
plasticity none
{config/elastic_Ti.config}
{config/thermal.config}
{config/thermalExpansion_Ti.config}
#--------------------------#
<microstructure>
#--------------------------#
[isotropic matrix]
crystallite 1
(constituent) phase 1 texture 1 fraction 1.0
[Ti matrix]
crystallite 1
(constituent) phase 2 texture 1 fraction 1.0
[isotropic inclusion]
crystallite 1
(constituent) phase 3 texture 1 fraction 1.0
[anisotropic inclusion]
crystallite 1
(constituent) phase 4 texture 1 fraction 1.0
[rotated inclusion]
crystallite 1
(constituent) phase 4 texture 2 fraction 1.0
[Ti inclusion]
crystallite 1
(constituent) phase 5 texture 1 fraction 1.0
#--------------------------#
<texture>
#--------------------------#
[cube]
(gauss) phi1 0.0 Phi 0.0 phi2 0.0 scatter 0.0 fraction 1.0
[rotated]
(gauss) phi1 0.0 Phi 45.0 phi2 0.0 scatter 0.0 fraction 1.0

View File

@ -0,0 +1,5 @@
#spectralsolver polarisation
spectralderivative fwbw_difference
err_div_tolrel 1e-3
itmin 2
petsc_options -mech_snes_type anderson -mech_snes_anderson_beta 1.0 -mech_snes_anderson_restart 10 -thermal_snes_type anderson -thermal_snes_anderson_beta 1.0

View File

@ -0,0 +1,56 @@
#!/usr/local/bin/bash
for geom in $(ls geom/*.geom)
do
base=${geom%.geom}
base=${base#geom/}
name=${base}_thermal
vtr=${base}.vtr
[[ -f ${name}.spectralOut ]] || \
DAMASK_spectral \
--workingdir ./ \
--load thermal.load \
--geom $geom \
> ${name}.out
if [ ! -f postProc/${name}_inc10.txt ]
then
postResults ${name}.spectralOut \
--ho temperature \
--cr f,fe,fi,fp,p \
--split \
--separation x,y,z \
addCauchy postProc/${name}_inc*.txt \
addDeviator postProc/${name}_inc*.txt \
--spherical \
--tensor p,Cauchy \
addDisplacement postProc/${name}_inc*.txt \
--nodal \
fi
geom_check ${geom}
for inc in {00..10}
do
echo "generating postProc/${name}_inc${inc}.vtr"
cp geom/${vtr} postProc/${name}_inc${inc}.vtr
vtk_addRectilinearGridData \
postProc/${name}_inc${inc}.txt \
--inplace \
--vtk postProc/${name}_inc${inc}.vtr \
--data 'sph(p)','sph(Cauchy)',temperature \
--tensor f,fe,fi,fp,p,Cauchy \
vtk_addRectilinearGridData \
postProc/${name}_inc${inc}_nodal.txt \
--inplace \
--vtk postProc/${name}_inc${inc}.vtr \
--data 'avg(f).pos','fluct(f).pos' \
done
done

View File

@ -0,0 +1 @@
Fdot 0 0 0 0 0 0 0 0 0 stress * * * * * * * * * time 1000 incs 10

View File

@ -29,9 +29,14 @@ parser.add_option('-m', '--microstructureoffset',
type = 'int', metavar = 'int', type = 'int', metavar = 'int',
help = 'offset (positive or negative) for tagged microstructure indices. '+ help = 'offset (positive or negative) for tagged microstructure indices. '+
'"0" selects maximum microstructure index [%default]') '"0" selects maximum microstructure index [%default]')
parser.add_option('-n', '--nonperiodic',
dest = 'mode',
action = 'store_const', const = 'nearest',
help = 'assume geometry to be non-periodic')
parser.set_defaults(vicinity = 1, parser.set_defaults(vicinity = 1,
offset = 0, offset = 0,
mode = 'wrap',
) )
(options, filenames) = parser.parse_args() (options, filenames) = parser.parse_args()
@ -79,8 +84,8 @@ for name in filenames:
if options.offset == 0: options.offset = microstructure.max() if options.offset == 0: options.offset = microstructure.max()
microstructure = np.where(ndimage.filters.maximum_filter(microstructure,size=1+2*options.vicinity,mode='wrap') == microstructure = np.where(ndimage.filters.maximum_filter(microstructure,size=1+2*options.vicinity,mode=options.mode) ==
ndimage.filters.minimum_filter(microstructure,size=1+2*options.vicinity,mode='wrap'), ndimage.filters.minimum_filter(microstructure,size=1+2*options.vicinity,mode=options.mode),
microstructure, microstructure + options.offset) microstructure, microstructure + options.offset)
newInfo['microstructures'] = microstructure.max() newInfo['microstructures'] = microstructure.max()

View File

@ -9,7 +9,7 @@ module CPFEM2
private private
public :: & public :: &
CPFEM_general, & CPFEM_age, &
CPFEM_initAll CPFEM_initAll
contains contains
@ -127,6 +127,7 @@ subroutine CPFEM_init
write(6,'(/,a)') ' <<<+- CPFEM init -+>>>' write(6,'(/,a)') ' <<<+- CPFEM init -+>>>'
write(6,'(a15,a)') ' Current time: ',IO_timeStamp() write(6,'(a15,a)') ' Current time: ',IO_timeStamp()
#include "compilation_info.f90" #include "compilation_info.f90"
flush(6)
endif mainProcess endif mainProcess
! *** restore the last converged values of each essential variable from the binary file ! *** restore the last converged values of each essential variable from the binary file
@ -139,36 +140,28 @@ subroutine CPFEM_init
write(rankStr,'(a1,i0)')'_',worldrank write(rankStr,'(a1,i0)')'_',worldrank
call IO_read_intFile(777,'recordedPhase'//trim(rankStr),modelName,size(material_phase)) call IO_read_intFile(777,'recordedPhase'//trim(rankStr),modelName,size(material_phase))
read (777,rec=1) material_phase read (777,rec=1) material_phase; close (777)
close (777)
call IO_read_realFile(777,'convergedF'//trim(rankStr),modelName,size(crystallite_F0)) call IO_read_realFile(777,'convergedF'//trim(rankStr),modelName,size(crystallite_F0))
read (777,rec=1) crystallite_F0 read (777,rec=1) crystallite_F0; close (777)
close (777)
call IO_read_realFile(777,'convergedFp'//trim(rankStr),modelName,size(crystallite_Fp0)) call IO_read_realFile(777,'convergedFp'//trim(rankStr),modelName,size(crystallite_Fp0))
read (777,rec=1) crystallite_Fp0 read (777,rec=1) crystallite_Fp0; close (777)
close (777)
call IO_read_realFile(777,'convergedFi'//trim(rankStr),modelName,size(crystallite_Fi0)) call IO_read_realFile(777,'convergedFi'//trim(rankStr),modelName,size(crystallite_Fi0))
read (777,rec=1) crystallite_Fi0 read (777,rec=1) crystallite_Fi0; close (777)
close (777)
call IO_read_realFile(777,'convergedLp'//trim(rankStr),modelName,size(crystallite_Lp0)) call IO_read_realFile(777,'convergedLp'//trim(rankStr),modelName,size(crystallite_Lp0))
read (777,rec=1) crystallite_Lp0 read (777,rec=1) crystallite_Lp0; close (777)
close (777)
call IO_read_realFile(777,'convergedLi'//trim(rankStr),modelName,size(crystallite_Li0)) call IO_read_realFile(777,'convergedLi'//trim(rankStr),modelName,size(crystallite_Li0))
read (777,rec=1) crystallite_Li0 read (777,rec=1) crystallite_Li0; close (777)
close (777)
call IO_read_realFile(777,'convergeddPdF'//trim(rankStr),modelName,size(crystallite_dPdF0)) call IO_read_realFile(777,'convergeddPdF'//trim(rankStr),modelName,size(crystallite_dPdF0))
read (777,rec=1) crystallite_dPdF0 read (777,rec=1) crystallite_dPdF0; close (777)
close (777)
call IO_read_realFile(777,'convergedTstar'//trim(rankStr),modelName,size(crystallite_Tstar0_v)) call IO_read_realFile(777,'convergedTstar'//trim(rankStr),modelName,size(crystallite_Tstar0_v))
read (777,rec=1) crystallite_Tstar0_v read (777,rec=1) crystallite_Tstar0_v; close (777)
close (777)
call IO_read_realFile(777,'convergedStateConst'//trim(rankStr),modelName) call IO_read_realFile(777,'convergedStateConst'//trim(rankStr),modelName)
m = 0_pInt m = 0_pInt
@ -194,7 +187,6 @@ subroutine CPFEM_init
restartRead = .false. restartRead = .false.
endif endif
flush(6)
end subroutine CPFEM_init end subroutine CPFEM_init
@ -202,7 +194,7 @@ end subroutine CPFEM_init
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief perform initialization at first call, update variables and call the actual material model !> @brief perform initialization at first call, update variables and call the actual material model
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine CPFEM_general(age, dt) subroutine CPFEM_age()
use prec, only: & use prec, only: &
pReal, & pReal, &
pInt pInt
@ -215,7 +207,6 @@ subroutine CPFEM_general(age, dt)
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective debug_levelSelective
use FEsolving, only: & use FEsolving, only: &
terminallyIll, &
restartWrite restartWrite
use math, only: & use math, only: &
math_identity2nd, & math_identity2nd, &
@ -254,85 +245,71 @@ subroutine CPFEM_general(age, dt)
crystallite_dPdF, & crystallite_dPdF, &
crystallite_Tstar0_v, & crystallite_Tstar0_v, &
crystallite_Tstar_v crystallite_Tstar_v
use homogenization, only: &
materialpoint_stressAndItsTangent, &
materialpoint_postResults
use IO, only: & use IO, only: &
IO_write_jobRealFile, & IO_write_jobRealFile, &
IO_warning IO_warning
use DAMASK_interface use DAMASK_interface
implicit none implicit none
real(pReal), intent(in) :: dt !< time increment
logical, intent(in) :: age !< age results
integer(pInt) :: i, k, l, m, ph, homog, mySource integer(pInt) :: i, k, l, m, ph, homog, mySource
character(len=1024) :: rankStr character(len=32) :: rankStr
!*** age results and write restart data if requested if (iand(debug_level(debug_CPFEM), debug_levelBasic) /= 0_pInt) &
if (age) then
crystallite_F0 = crystallite_partionedF ! crystallite deformation (_subF is perturbed...)
crystallite_Fp0 = crystallite_Fp ! crystallite plastic deformation
crystallite_Lp0 = crystallite_Lp ! crystallite plastic velocity
crystallite_Fi0 = crystallite_Fi ! crystallite intermediate deformation
crystallite_Li0 = crystallite_Li ! crystallite intermediate velocity
crystallite_dPdF0 = crystallite_dPdF ! crystallite stiffness
crystallite_Tstar0_v = crystallite_Tstar_v ! crystallite 2nd Piola Kirchhoff stress
forall ( i = 1:size(plasticState )) plasticState(i)%state0 = plasticState(i)%state ! copy state in this lenghty way because: A component cannot be an array if the encompassing structure is an array
do i = 1, size(sourceState)
do mySource = 1,phase_Nsources(i)
sourceState(i)%p(mySource)%state0 = sourceState(i)%p(mySource)%state ! copy state in this lenghty way because: A component cannot be an array if the encompassing structure is an array
enddo; enddo
if (iand(debug_level(debug_CPFEM), debug_levelBasic) /= 0_pInt) &
write(6,'(a)') '<< CPFEM >> aging states' write(6,'(a)') '<< CPFEM >> aging states'
do homog = 1_pInt, material_Nhomogenization crystallite_F0 = crystallite_partionedF ! crystallite deformation (_subF is perturbed...)
crystallite_Fp0 = crystallite_Fp ! crystallite plastic deformation
crystallite_Lp0 = crystallite_Lp ! crystallite plastic velocity
crystallite_Fi0 = crystallite_Fi ! crystallite intermediate deformation
crystallite_Li0 = crystallite_Li ! crystallite intermediate velocity
crystallite_dPdF0 = crystallite_dPdF ! crystallite stiffness
crystallite_Tstar0_v = crystallite_Tstar_v ! crystallite 2nd Piola Kirchhoff stress
forall (i = 1:size(plasticState)) plasticState(i)%state0 = plasticState(i)%state ! copy state in this lengthy way because: A component cannot be an array if the encompassing structure is an array
do i = 1, size(sourceState)
do mySource = 1,phase_Nsources(i)
sourceState(i)%p(mySource)%state0 = sourceState(i)%p(mySource)%state ! copy state in this lengthy way because: A component cannot be an array if the encompassing structure is an array
enddo; enddo
do homog = 1_pInt, material_Nhomogenization
homogState (homog)%state0 = homogState (homog)%state homogState (homog)%state0 = homogState (homog)%state
thermalState (homog)%state0 = thermalState (homog)%state thermalState (homog)%state0 = thermalState (homog)%state
damageState (homog)%state0 = damageState (homog)%state damageState (homog)%state0 = damageState (homog)%state
vacancyfluxState (homog)%state0 = vacancyfluxState (homog)%state vacancyfluxState (homog)%state0 = vacancyfluxState (homog)%state
hydrogenfluxState(homog)%state0 = hydrogenfluxState(homog)%state hydrogenfluxState(homog)%state0 = hydrogenfluxState(homog)%state
enddo enddo
if (restartWrite) then
if (restartWrite) then
if (iand(debug_level(debug_CPFEM), debug_levelBasic) /= 0_pInt) & if (iand(debug_level(debug_CPFEM), debug_levelBasic) /= 0_pInt) &
write(6,'(a)') '<< CPFEM >> writing state variables of last converged step to binary files' write(6,'(a)') '<< CPFEM >> writing state variables of last converged step to binary files'
write(rankStr,'(a1,i0)')'_',worldrank write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'recordedPhase'//trim(rankStr),size(material_phase)) call IO_write_jobRealFile(777,'recordedPhase'//trim(rankStr),size(material_phase))
write (777,rec=1) material_phase write (777,rec=1) material_phase; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedF'//trim(rankStr),size(crystallite_F0)) call IO_write_jobRealFile(777,'convergedF'//trim(rankStr),size(crystallite_F0))
write (777,rec=1) crystallite_F0 write (777,rec=1) crystallite_F0; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedFp'//trim(rankStr),size(crystallite_Fp0)) call IO_write_jobRealFile(777,'convergedFp'//trim(rankStr),size(crystallite_Fp0))
write (777,rec=1) crystallite_Fp0 write (777,rec=1) crystallite_Fp0; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedFi'//trim(rankStr),size(crystallite_Fi0)) call IO_write_jobRealFile(777,'convergedFi'//trim(rankStr),size(crystallite_Fi0))
write (777,rec=1) crystallite_Fi0 write (777,rec=1) crystallite_Fi0; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedLp'//trim(rankStr),size(crystallite_Lp0)) call IO_write_jobRealFile(777,'convergedLp'//trim(rankStr),size(crystallite_Lp0))
write (777,rec=1) crystallite_Lp0 write (777,rec=1) crystallite_Lp0; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedLi'//trim(rankStr),size(crystallite_Li0)) call IO_write_jobRealFile(777,'convergedLi'//trim(rankStr),size(crystallite_Li0))
write (777,rec=1) crystallite_Li0 write (777,rec=1) crystallite_Li0; close (777)
close (777)
call IO_write_jobRealFile(777,'convergeddPdF'//trim(rankStr),size(crystallite_dPdF0)) call IO_write_jobRealFile(777,'convergeddPdF'//trim(rankStr),size(crystallite_dPdF0))
write (777,rec=1) crystallite_dPdF0 write (777,rec=1) crystallite_dPdF0; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedTstar'//trim(rankStr),size(crystallite_Tstar0_v)) call IO_write_jobRealFile(777,'convergedTstar'//trim(rankStr),size(crystallite_Tstar0_v))
write (777,rec=1) crystallite_Tstar0_v write (777,rec=1) crystallite_Tstar0_v; close (777)
close (777)
call IO_write_jobRealFile(777,'convergedStateConst'//trim(rankStr)) call IO_write_jobRealFile(777,'convergedStateConst'//trim(rankStr))
m = 0_pInt m = 0_pInt
@ -356,12 +333,11 @@ subroutine CPFEM_general(age, dt)
enddo writeHomogInstances enddo writeHomogInstances
close (777) close (777)
endif endif
endif
if (.not. terminallyIll) & if (iand(debug_level(debug_CPFEM), debug_levelBasic) /= 0_pInt) &
call materialpoint_stressAndItsTangent(.True., dt) write(6,'(a)') '<< CPFEM >> done aging states'
end subroutine CPFEM_general end subroutine CPFEM_age
end module CPFEM2 end module CPFEM2

246
src/DAMASK_spectral.f90 Normal file → Executable file
View File

@ -78,8 +78,7 @@ program DAMASK_spectral
FIELD_UNDEFINED_ID, & FIELD_UNDEFINED_ID, &
FIELD_MECH_ID, & FIELD_MECH_ID, &
FIELD_THERMAL_ID, & FIELD_THERMAL_ID, &
FIELD_DAMAGE_ID, & FIELD_DAMAGE_ID
utilities_calcPlasticity
use spectral_mech_Basic use spectral_mech_Basic
use spectral_mech_AL use spectral_mech_AL
use spectral_mech_Polarisation use spectral_mech_Polarisation
@ -157,19 +156,6 @@ program DAMASK_spectral
MPI_finalize, & MPI_finalize, &
MPI_allreduce, & MPI_allreduce, &
PETScFinalize PETScFinalize
!--------------------------------------------------------------------------------------------------
! variables related to stop criterion for yielding
real(pReal) :: plasticWorkOld, plasticWorkNew, & ! plastic work
eqTotalStrainOld, eqTotalStrainNew, & ! total equivalent strain
eqPlasticStrainOld, eqPlasticStrainNew, & ! total equivalent plastic strain
eqStressOld, eqStressNew , & ! equivalent stress
yieldStopValue
real(pReal), dimension(3,3) :: yieldStress,yieldStressOld,yieldStressNew, &
plasticStrainOld, plasticStrainNew, plasticStrainRate
integer(pInt) :: yieldResUnit = 0_pInt
integer(pInt) :: stressstrainUnit = 0_pInt
character(len=13) :: stopFlag
logical :: yieldStop, yieldStopSatisfied
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! init DAMASK (all modules) ! init DAMASK (all modules)
@ -227,8 +213,6 @@ program DAMASK_spectral
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! reading the load case and assign values to the allocated data structure ! reading the load case and assign values to the allocated data structure
yieldStop = .False.
yieldStopSatisfied = .False.
rewind(FILEUNIT) rewind(FILEUNIT)
do do
line = IO_read(FILEUNIT) line = IO_read(FILEUNIT)
@ -303,30 +287,10 @@ program DAMASK_spectral
temp_valueVector(j) = IO_floatValue(line,chunkPos,i+j) temp_valueVector(j) = IO_floatValue(line,chunkPos,i+j)
enddo enddo
loadCases(currentLoadCase)%rotation = math_plain9to33(temp_valueVector) loadCases(currentLoadCase)%rotation = math_plain9to33(temp_valueVector)
case('totalstrain')
yieldStop = .True.
stopFlag = 'totalStrain'
yieldStopValue = IO_floatValue(line,chunkPos,i+1_pInt)
case('plasticstrain')
yieldStop = .True.
stopFlag = 'plasticStrain'
yieldStopValue = IO_floatValue(line,chunkPos,i+1_pInt)
case('plasticwork')
yieldStop = .True.
stopFlag = 'plasticWork'
yieldStopValue = IO_floatValue(line,chunkPos,i+1_pInt)
end select end select
enddo; enddo enddo; enddo
close(FILEUNIT) close(FILEUNIT)
if(yieldStop) then ! initialize variables related to yield stop
yieldStressNew = 0.0_pReal
plasticStrainNew = 0.0_pReal
eqStressNew = 0.0_pReal
eqTotalStrainNew = 0.0_pReal
eqPlasticStrainNew = 0.0_pReal
plasticWorkNew = 0.0_pReal
endif
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! consistency checks and output of load case ! consistency checks and output of load case
loadCases(1)%followFormerTrajectory = .false. ! cannot guess along trajectory for first inc of first currentLoadCase loadCases(1)%followFormerTrajectory = .false. ! cannot guess along trajectory for first inc of first currentLoadCase
@ -443,7 +407,7 @@ program DAMASK_spectral
write(resUnit) 'times:', loadCases%time ! one entry per LoadCase write(resUnit) 'times:', loadCases%time ! one entry per LoadCase
write(resUnit) 'logscales:', loadCases%logscale write(resUnit) 'logscales:', loadCases%logscale
write(resUnit) 'increments:', loadCases%incs ! one entry per LoadCase write(resUnit) 'increments:', loadCases%incs ! one entry per LoadCase
write(resUnit) 'startingIncrement:', restartInc - 1_pInt ! start with writing out the previous inc write(resUnit) 'startingIncrement:', restartInc ! start with writing out the previous inc
write(resUnit) 'eoh' write(resUnit) 'eoh'
close(resUnit) ! end of header close(resUnit) ! end of header
open(newunit=statUnit,file=trim(getSolverWorkingDirectoryName())//trim(getSolverJobName())//& open(newunit=statUnit,file=trim(getSolverWorkingDirectoryName())//trim(getSolverJobName())//&
@ -478,8 +442,9 @@ program DAMASK_spectral
if (ierr /= 0_pInt) call IO_error(error_ID=894_pInt, ext_msg='MPI_file_seek') if (ierr /= 0_pInt) call IO_error(error_ID=894_pInt, ext_msg='MPI_file_seek')
if (.not. appendToOutFile) then ! if not restarting, write 0th increment if (.not. appendToOutFile) then ! if not restarting, write 0th increment
write(6,'(1/,a)') ' ... writing initial configuration to file ........................'
do i = 1, size(materialpoint_results,3)/(maxByteOut/(materialpoint_sizeResults*pReal))+1 ! slice the output of my process in chunks not exceeding the limit for one output do i = 1, size(materialpoint_results,3)/(maxByteOut/(materialpoint_sizeResults*pReal))+1 ! slice the output of my process in chunks not exceeding the limit for one output
outputIndex = int([(i-1_pInt)*((maxRealOut)/materialpoint_sizeResults)+1_pInt, & outputIndex = int([(i-1_pInt)*((maxRealOut)/materialpoint_sizeResults)+1_pInt, & ! QUESTION: why not starting i at 0 instead of murky 1?
min(i*((maxRealOut)/materialpoint_sizeResults),size(materialpoint_results,3))],pLongInt) min(i*((maxRealOut)/materialpoint_sizeResults),size(materialpoint_results,3))],pLongInt)
call MPI_file_write(resUnit, & call MPI_file_write(resUnit, &
reshape(materialpoint_results(:,:,outputIndex(1):outputIndex(2)), & reshape(materialpoint_results(:,:,outputIndex(1):outputIndex(2)), &
@ -489,24 +454,23 @@ program DAMASK_spectral
if (ierr /= 0_pInt) call IO_error(error_ID=894_pInt, ext_msg='MPI_file_write') if (ierr /= 0_pInt) call IO_error(error_ID=894_pInt, ext_msg='MPI_file_write')
enddo enddo
fileOffset = fileOffset + sum(outputSize) ! forward to current file position fileOffset = fileOffset + sum(outputSize) ! forward to current file position
write(6,'(1/,a)') ' ... writing initial configuration to file ........................'
endif endif
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! loopping over loadcases ! looping over loadcases
loadCaseLooping: do currentLoadCase = 1_pInt, size(loadCases) loadCaseLooping: do currentLoadCase = 1_pInt, size(loadCases)
time0 = time ! currentLoadCase start time time0 = time ! currentLoadCase start time
guess = loadCases(currentLoadCase)%followFormerTrajectory ! change of load case? homogeneous guess for the first inc guess = loadCases(currentLoadCase)%followFormerTrajectory ! change of load case? homogeneous guess for the first inc
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! loop oper incs defined in input file for current currentLoadCase ! loop over incs defined in input file for current currentLoadCase
incLooping: do inc = 1_pInt, loadCases(currentLoadCase)%incs incLooping: do inc = 1_pInt, loadCases(currentLoadCase)%incs
totalIncsCounter = totalIncsCounter + 1_pInt totalIncsCounter = totalIncsCounter + 1_pInt
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! forwarding time ! forwarding time
timeIncOld = timeinc timeIncOld = timeinc ! last timeinc that brought former inc to an end
if (loadCases(currentLoadCase)%logscale == 0_pInt) then ! linear scale if (loadCases(currentLoadCase)%logscale == 0_pInt) then ! linear scale
timeinc = loadCases(currentLoadCase)%time/real(loadCases(currentLoadCase)%incs,pReal) ! only valid for given linear time scale. will be overwritten later in case loglinear scale is used timeinc = loadCases(currentLoadCase)%time/real(loadCases(currentLoadCase)%incs,pReal)
else else
if (currentLoadCase == 1_pInt) then ! 1st currentLoadCase of logarithmic scale if (currentLoadCase == 1_pInt) then ! 1st currentLoadCase of logarithmic scale
if (inc == 1_pInt) then ! 1st inc of 1st currentLoadCase of logarithmic scale if (inc == 1_pInt) then ! 1st inc of 1st currentLoadCase of logarithmic scale
@ -516,40 +480,46 @@ program DAMASK_spectral
endif endif
else ! not-1st currentLoadCase of logarithmic scale else ! not-1st currentLoadCase of logarithmic scale
timeinc = time0 * & timeinc = time0 * &
( (1.0_pReal + loadCases(currentLoadCase)%time/time0 )**(real( inc,pReal)/& ( (1.0_pReal + loadCases(currentLoadCase)%time/time0 )**(real( inc ,pReal)/&
real(loadCases(currentLoadCase)%incs ,pReal))& real(loadCases(currentLoadCase)%incs ,pReal))&
-(1.0_pReal + loadCases(currentLoadCase)%time/time0 )**(real( (inc-1_pInt),pReal)/& -(1.0_pReal + loadCases(currentLoadCase)%time/time0 )**(real( inc-1_pInt ,pReal)/&
real(loadCases(currentLoadCase)%incs ,pReal))) real(loadCases(currentLoadCase)%incs ,pReal)))
endif endif
endif endif
timeinc = timeinc / 2.0_pReal**real(cutBackLevel,pReal) ! depending on cut back level, decrease time step timeinc = timeinc * real(subStepFactor,pReal)**real(-cutBackLevel,pReal) ! depending on cut back level, decrease time step
forwarding: if (totalIncsCounter >= restartInc) then skipping: if (totalIncsCounter <= restartInc) then ! not yet at restart inc?
stepFraction = 0_pInt time = time + timeinc ! just advance time, skip already performed calculation
guess = .true. ! QUESTION:why forced guessing instead of inheriting loadcase preference
else skipping
stepFraction = 0_pInt ! fraction scaled by stepFactor**cutLevel
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! loop over sub incs ! loop over sub step
subIncLooping: do while (stepFraction/subStepFactor**cutBackLevel <1_pInt) subStepLooping: do while (stepFraction < subStepFactor**cutBackLevel)
time = time + timeinc ! forward time remainingLoadCaseTime = loadCases(currentLoadCase)%time+time0 - time
stepFraction = stepFraction + 1_pInt time = time + timeinc ! forward target time
remainingLoadCaseTime = time0 - time + loadCases(currentLoadCase)%time + timeInc stepFraction = stepFraction + 1_pInt ! count step
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report begin of new increment ! report begin of new step
write(6,'(/,a)') ' ###########################################################################' write(6,'(/,a)') ' ###########################################################################'
write(6,'(1x,a,es12.5'//& write(6,'(1x,a,es12.5'//&
',a,'//IO_intOut(inc)//',a,'//IO_intOut(loadCases(currentLoadCase)%incs)//& ',a,'//IO_intOut(inc) //',a,'//IO_intOut(loadCases(currentLoadCase)%incs)//&
',a,'//IO_intOut(stepFraction)//',a,'//IO_intOut(subStepFactor**cutBackLevel)//& ',a,'//IO_intOut(stepFraction) //',a,'//IO_intOut(subStepFactor**cutBackLevel)//&
',a,'//IO_intOut(currentLoadCase)//',a,'//IO_intOut(size(loadCases))//')') & ',a,'//IO_intOut(currentLoadCase)//',a,'//IO_intOut(size(loadCases))//')') &
'Time', time, & 'Time', time, &
's: Increment ', inc, '/', loadCases(currentLoadCase)%incs,& 's: Increment ', inc,'/',loadCases(currentLoadCase)%incs,&
'-', stepFraction, '/', subStepFactor**cutBackLevel,& '-', stepFraction,'/',subStepFactor**cutBackLevel,&
' of load case ', currentLoadCase,'/',size(loadCases) ' of load case ', currentLoadCase,'/',size(loadCases)
flush(6) write(incInfo,&
write(incInfo,'(a,'//IO_intOut(totalIncsCounter)//',a,'//IO_intOut(sum(loadCases%incs))//& '(a,'//IO_intOut(totalIncsCounter)//&
',a,'//IO_intOut(stepFraction)//',a,'//IO_intOut(subStepFactor**cutBackLevel)//')') & ',a,'//IO_intOut(sum(loadCases%incs))//&
',a,'//IO_intOut(stepFraction)//&
',a,'//IO_intOut(subStepFactor**cutBackLevel)//')') &
'Increment ',totalIncsCounter,'/',sum(loadCases%incs),& 'Increment ',totalIncsCounter,'/',sum(loadCases%incs),&
'-',stepFraction, '/', subStepFactor**cutBackLevel '-', stepFraction,'/',subStepFactor**cutBackLevel
flush(6)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! forward fields ! forward fields
@ -618,65 +588,63 @@ program DAMASK_spectral
solres(field) = spectral_damage_solution(timeinc,timeIncOld,remainingLoadCaseTime) solres(field) = spectral_damage_solution(timeinc,timeIncOld,remainingLoadCaseTime)
end select end select
if (.not. solres(field)%converged) exit ! no solution found if (.not. solres(field)%converged) exit ! no solution found
enddo enddo
stagIter = stagIter + 1_pInt stagIter = stagIter + 1_pInt
stagIterate = stagIter < stagItMax .and. & stagIterate = stagIter < stagItMax &
all(solres(:)%converged) .and. & .and. all(solres(:)%converged) &
.not. all(solres(:)%stagConverged) .and. .not. all(solres(:)%stagConverged) ! stationary with respect to staggered iteration
enddo enddo
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! check solution ! check solution for either advance or retry
cutBack = .False.
if(solres(1)%termIll .or. .not. all(solres(:)%converged .and. solres(:)%stagConverged)) then ! no solution found if ( (continueCalculation .or. all(solres(:)%converged .and. solres(:)%stagConverged)) & ! don't care or did converge
if (cutBackLevel < maxCutBack) then ! do cut back .and. .not. solres(1)%termIll) then ! and acceptable solution found
write(6,'(/,a)') ' cut back detected' timeIncOld = timeinc
cutBack = .True. cutBack = .false.
guess = .true. ! start guessing after first converged (sub)inc
if (worldrank == 0) then
write(statUnit,*) totalIncsCounter, time, cutBackLevel, &
solres%converged, solres%iterationsNeeded
flush(statUnit)
endif
elseif (cutBackLevel < maxCutBack) then ! further cutbacking tolerated?
cutBack = .true.
stepFraction = (stepFraction - 1_pInt) * subStepFactor ! adjust to new denominator stepFraction = (stepFraction - 1_pInt) * subStepFactor ! adjust to new denominator
cutBackLevel = cutBackLevel + 1_pInt cutBackLevel = cutBackLevel + 1_pInt
time = time - timeinc ! rewind time time = time - timeinc ! rewind time
timeinc = timeinc/2.0_pReal timeinc = timeinc/real(subStepFactor,pReal) ! cut timestep
elseif (solres(1)%termIll) then ! material point model cannot find a solution, exit in any casy write(6,'(/,a)') ' cutting back '
call IO_warning(850_pInt) else ! no more options to continue
call MPI_file_close(resUnit,ierr)
close(statUnit)
call quit(-1_pInt*(lastRestartWritten+1_pInt)) ! quit and provide information about last restart inc written
elseif (continueCalculation == 1_pInt) then
guess = .true. ! accept non converged BVP solution
else ! default behavior, exit if spectral solver does not converge
call IO_warning(850_pInt) call IO_warning(850_pInt)
call MPI_file_close(resUnit,ierr) call MPI_file_close(resUnit,ierr)
close(statUnit) close(statUnit)
call quit(-1_pInt*(lastRestartWritten+1_pInt)) ! quit and provide information about last restart inc written call quit(-1_pInt*(lastRestartWritten+1_pInt)) ! quit and provide information about last restart inc written
endif endif
else
guess = .true. ! start guessing after first converged (sub)inc enddo subStepLooping
endif
if (.not. cutBack) then
if (worldrank == 0) then
write(statUnit,*) totalIncsCounter, time, cutBackLevel, &
solres%converged, solres%iterationsNeeded ! write statistics about accepted solution
flush(statUnit)
endif
endif
enddo subIncLooping
cutBackLevel = max(0_pInt, cutBackLevel - 1_pInt) ! try half number of subincs next inc cutBackLevel = max(0_pInt, cutBackLevel - 1_pInt) ! try half number of subincs next inc
if(all(solres(:)%converged)) then ! report converged inc
if (all(solres(:)%converged)) then
convergedCounter = convergedCounter + 1_pInt convergedCounter = convergedCounter + 1_pInt
write(6,'(/,a,'//IO_intOut(totalIncsCounter)//',a)') & write(6,'(/,a,'//IO_intOut(totalIncsCounter)//',a)') & ! report converged inc
' increment ', totalIncsCounter, ' converged' ' increment ', totalIncsCounter, ' converged'
else else
notConvergedCounter = notConvergedCounter + 1_pInt
write(6,'(/,a,'//IO_intOut(totalIncsCounter)//',a)') & ! report non-converged inc write(6,'(/,a,'//IO_intOut(totalIncsCounter)//',a)') & ! report non-converged inc
' increment ', totalIncsCounter, ' NOT converged' ' increment ', totalIncsCounter, ' NOT converged'
notConvergedCounter = notConvergedCounter + 1_pInt
endif; flush(6) endif; flush(6)
if (mod(inc,loadCases(currentLoadCase)%outputFrequency) == 0_pInt) then ! at output frequency if (mod(inc,loadCases(currentLoadCase)%outputFrequency) == 0_pInt) then ! at output frequency
if (worldrank == 0) &
write(6,'(1/,a)') ' ... writing results to file ......................................' write(6,'(1/,a)') ' ... writing results to file ......................................'
flush(6)
call materialpoint_postResults() call materialpoint_postResults()
call MPI_file_seek (resUnit,fileOffset,MPI_SEEK_SET,ierr) call MPI_file_seek (resUnit,fileOffset,MPI_SEEK_SET,ierr)
if(ierr /=0_pInt) call IO_error(894_pInt, ext_msg='MPI_file_seek') if (ierr /= 0_pInt) call IO_error(894_pInt, ext_msg='MPI_file_seek')
do i=1, size(materialpoint_results,3)/(maxByteOut/(materialpoint_sizeResults*pReal))+1 ! slice the output of my process in chunks not exceeding the limit for one output do i=1, size(materialpoint_results,3)/(maxByteOut/(materialpoint_sizeResults*pReal))+1 ! slice the output of my process in chunks not exceeding the limit for one output
outputIndex=int([(i-1_pInt)*((maxRealOut)/materialpoint_sizeResults)+1_pInt, & outputIndex=int([(i-1_pInt)*((maxRealOut)/materialpoint_sizeResults)+1_pInt, &
min(i*((maxRealOut)/materialpoint_sizeResults),size(materialpoint_results,3))],pLongInt) min(i*((maxRealOut)/materialpoint_sizeResults),size(materialpoint_results,3))],pLongInt)
@ -688,93 +656,29 @@ program DAMASK_spectral
enddo enddo
fileOffset = fileOffset + sum(outputSize) ! forward to current file position fileOffset = fileOffset + sum(outputSize) ! forward to current file position
endif endif
if( loadCases(currentLoadCase)%restartFrequency > 0_pInt .and. & ! at frequency of writing restart information set restart parameter for FEsolving if ( loadCases(currentLoadCase)%restartFrequency > 0_pInt & ! writing of restart info requested ...
mod(inc,loadCases(currentLoadCase)%restartFrequency) == 0_pInt) then ! first call to CPFEM_general will write? .and. mod(inc,loadCases(currentLoadCase)%restartFrequency) == 0_pInt) then ! ... and at frequency of writing restart information
restartWrite = .true. restartWrite = .true. ! set restart parameter for FEsolving
lastRestartWritten = inc lastRestartWritten = inc ! QUESTION: first call to CPFEM_general will write?
endif
else forwarding
time = time + timeinc
guess = .true.
endif forwarding
yieldCheck: if(yieldStop) then ! check if it yields or satisfies the certain stop condition
yieldStressOld = yieldStressNew
plasticStrainOld = plasticStrainNew
eqStressOld = eqStressNew
eqTotalStrainOld = eqTotalStrainNew
eqPlasticStrainOld = eqPlasticStrainNew
plasticWorkOld = plasticWorkNew
call utilities_calcPlasticity(yieldStressNew, plasticStrainNew, eqStressNew, eqTotalStrainNew, &
eqPlasticStrainNew, plasticWorkNew, loadCases(currentLoadCase)%rotation)
if (worldrank == 0) then ! output the stress-strain curve to file if yield stop criterion is used
if ((currentLoadCase == 1_pInt) .and. (inc == 1_pInt)) then
open(newunit=stressstrainUnit,file=trim(getSolverWorkingDirectoryName())//trim(getSolverJobName())//&
'.stressstrain',form='FORMATTED',status='REPLACE')
write(stressstrainUnit,*) 0.0_pReal, 0.0_pReal
write(stressstrainUnit,*) eqTotalStrainNew, eqStressNew
close(stressstrainUnit)
else
open(newunit=stressstrainUnit,file=trim(getSolverWorkingDirectoryName())//trim(getSolverJobName())//&
'.stressstrain',form='FORMATTED', position='APPEND', status='OLD')
write(stressstrainUnit,*) eqTotalStrainNew, eqStressNew
close(stressstrainUnit)
endif
endif endif
if(stopFlag == 'totalStrain') then endif skipping
if(eqTotalStrainNew > yieldStopValue) then
yieldStress = yieldStressOld * (eqTotalStrainNew - yieldStopValue)/(eqTotalStrainNew - eqTotalStrainOld) & ! linear interpolation of stress values
+ yieldStressNew * (yieldStopValue - eqTotalStrainOld)/(eqTotalStrainNew - eqTotalStrainOld)
plasticStrainRate = (plasticStrainNew - plasticStrainOld)/(time - time0) ! calculate plastic strain rate
yieldStopSatisfied = .True.
endif
elseif(stopFlag == 'plasticStrain') then
if(eqPlasticStrainNew > yieldStopValue) then
yieldStress = yieldStressOld * (eqPlasticStrainNew - yieldStopValue)/(eqPlasticStrainNew - eqPlasticStrainOld) &
+ yieldStressNew * (yieldStopValue - eqPlasticStrainOld)/(eqPlasticStrainNew - eqPlasticStrainOld)
plasticStrainRate = (plasticStrainNew - plasticStrainOld)/(time - time0)
yieldStopSatisfied = .True.
endif
elseif(stopFlag == 'plasticWork') then
if(plasticWorkNew > yieldStopValue) then
yieldStress = yieldStressOld * (plasticWorkNew - yieldStopValue)/(plasticWorkNew - plasticWorkOld) &
+ yieldStressNew * (yieldStopValue - plasticWorkOld)/(plasticWorkNew - plasticWorkOld)
plasticStrainRate = (plasticStrainNew - plasticStrainOld)/(time - time0)
yieldStopSatisfied = .True.
endif
endif
endif yieldCheck
if (yieldStopSatisfied) then ! when yield, write the yield stress and strain rate to file and quit the job
if (worldrank == 0) then
open(newunit=yieldResUnit,file=trim(getSolverWorkingDirectoryName())//trim(getSolverJobName())//&
'.yield',form='FORMATTED',status='REPLACE')
do i = 1_pInt,3_pInt
write(yieldResUnit,*) (yieldStress(i,j), j=1,3)
enddo
do i = 1_pInt,3_pInt
write(yieldResUnit,*) (plasticStrainRate(i,j), j=1,3)
enddo
close(yieldResUnit)
call quit(0_pInt)
endif
endif
enddo incLooping enddo incLooping
enddo loadCaseLooping enddo loadCaseLooping
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report summary of whole calculation ! report summary of whole calculation
write(6,'(/,a)') ' ###########################################################################' write(6,'(/,a)') ' ###########################################################################'
write(6,'(1x,i6.6,a,i6.6,a,f5.1,a)') convergedCounter, ' out of ', & write(6,'(1x,'//IO_intOut(convergedCounter)//',a,'//IO_intOut(notConvergedCounter + convergedCounter)//',a,f5.1,a)') &
convergedCounter, ' out of ', &
notConvergedCounter + convergedCounter, ' (', & notConvergedCounter + convergedCounter, ' (', &
real(convergedCounter, pReal)/& real(convergedCounter, pReal)/&
real(notConvergedCounter + convergedCounter,pReal)*100.0_pReal, & real(notConvergedCounter + convergedCounter,pReal)*100.0_pReal, &
' %) increments converged!' ' %) increments converged!'
flush(6)
call MPI_file_close(resUnit,ierr) call MPI_file_close(resUnit,ierr)
close(statUnit) close(statUnit)
@ -831,8 +735,6 @@ subroutine quit(stop_id)
call PETScFinalize(ierr) call PETScFinalize(ierr)
if (ierr /= 0) write(6,'(a)') ' Error in PETScFinalize' if (ierr /= 0) write(6,'(a)') ' Error in PETScFinalize'
#ifdef _OPENMP #ifdef _OPENMP
! If openMP is enabled, MPI is initialized before and independently of PETSc. Hence, also
! take care of the finalization
call MPI_finalize(error) call MPI_finalize(error)
if (error /= 0) write(6,'(a)') ' Error in MPI_finalize' if (error /= 0) write(6,'(a)') ' Error in MPI_finalize'
#endif #endif

View File

@ -79,20 +79,22 @@ subroutine FE_init
#include "compilation_info.f90" #include "compilation_info.f90"
modelName = getSolverJobName() modelName = getSolverJobName()
#if defined(Spectral) || defined(FEM)
#ifdef Spectral #ifdef Spectral
restartInc = spectralRestartInc restartInc = spectralRestartInc
if(restartInc <= 0_pInt) then #endif
call IO_warning(warning_ID=34_pInt) #ifdef FEM
restartInc = 1_pInt
endif
restartRead = restartInc > 1_pInt ! only read in if "true" restart requested
#elif defined FEM
restartInc = FEMRestartInc restartInc = FEMRestartInc
if(restartInc <= 0_pInt) then #endif
if(restartInc < 0_pInt) then
call IO_warning(warning_ID=34_pInt) call IO_warning(warning_ID=34_pInt)
restartInc = 1_pInt restartInc = 0_pInt
endif endif
restartRead = restartInc > 1_pInt restartRead = restartInc > 0_pInt ! only read in if "true" restart requested
#else #else
call IO_open_inputFile(FILEUNIT,modelName) call IO_open_inputFile(FILEUNIT,modelName)
rewind(FILEUNIT) rewind(FILEUNIT)
@ -131,19 +133,19 @@ subroutine FE_init
do do
read (FILEUNIT,'(a1024)',END=200) line read (FILEUNIT,'(a1024)',END=200) line
chunkPos = IO_stringPos(line) chunkPos = IO_stringPos(line)
if ( IO_lc(IO_stringValue(line,chunkPos,1_pInt)) == 'restart' .and. & if ( IO_lc(IO_stringValue(line,chunkPos,1_pInt)) == 'restart' &
IO_lc(IO_stringValue(line,chunkPos,2_pInt)) == 'file' .and. & .and. IO_lc(IO_stringValue(line,chunkPos,2_pInt)) == 'file' &
IO_lc(IO_stringValue(line,chunkPos,3_pInt)) == 'job' .and. & .and. IO_lc(IO_stringValue(line,chunkPos,3_pInt)) == 'job' &
IO_lc(IO_stringValue(line,chunkPos,4_pInt)) == 'id' ) & .and. IO_lc(IO_stringValue(line,chunkPos,4_pInt)) == 'id' ) &
modelName = IO_StringValue(line,chunkPos,6_pInt) modelName = IO_StringValue(line,chunkPos,6_pInt)
enddo enddo
#else #else ! QUESTION: is this meaningful for the spectral/FEM case?
call IO_open_inputFile(FILEUNIT,modelName) call IO_open_inputFile(FILEUNIT,modelName)
rewind(FILEUNIT) rewind(FILEUNIT)
do do
read (FILEUNIT,'(a1024)',END=200) line read (FILEUNIT,'(a1024)',END=200) line
chunkPos = IO_stringPos(line) chunkPos = IO_stringPos(line)
if ( IO_lc(IO_stringValue(line,chunkPos,1_pInt))=='*heading') then if (IO_lc(IO_stringValue(line,chunkPos,1_pInt))=='*heading') then
read (FILEUNIT,'(a1024)',END=200) line read (FILEUNIT,'(a1024)',END=200) line
chunkPos = IO_stringPos(line) chunkPos = IO_stringPos(line)
modelName = IO_StringValue(line,chunkPos,1_pInt) modelName = IO_StringValue(line,chunkPos,1_pInt)

View File

@ -1268,11 +1268,11 @@ integer(pInt) function IO_countNumericalDataLines(fileUnit)
line = IO_read(fileUnit) line = IO_read(fileUnit)
chunkPos = IO_stringPos(line) chunkPos = IO_stringPos(line)
tmp = IO_lc(IO_stringValue(line,chunkPos,1_pInt)) tmp = IO_lc(IO_stringValue(line,chunkPos,1_pInt))
if (verify(trim(tmp) ,"0123456789")/=0) then ! found keyword if (verify(trim(tmp),'0123456789') == 0) then ! numerical values
IO_countNumericalDataLines = IO_countNumericalDataLines + 1_pInt
else
line = IO_read(fileUnit, .true.) ! reset IO_read line = IO_read(fileUnit, .true.) ! reset IO_read
exit exit
else
IO_countNumericalDataLines = IO_countNumericalDataLines + 1_pInt
endif endif
enddo enddo
backspace(fileUnit) backspace(fileUnit)

View File

@ -885,7 +885,8 @@ subroutine constitutive_collectDotState(Tstar_v, FeArray, FpArray, subdt, subfra
real(pReal), intent(in), dimension(6) :: & real(pReal), intent(in), dimension(6) :: &
Tstar_v !< 2nd Piola Kirchhoff stress tensor (Mandel) Tstar_v !< 2nd Piola Kirchhoff stress tensor (Mandel)
integer(pLongInt) :: & integer(pLongInt) :: &
tick, tock, & tick = 0_pLongInt, &
tock = 0_pLongInt, &
tickrate, & tickrate, &
maxticks maxticks
integer(pInt) :: & integer(pInt) :: &

58
src/crystallite.f90 Normal file → Executable file
View File

@ -55,14 +55,14 @@ module crystallite
crystallite_Li0, & !< intermediate velocitiy grad at start of FE inc crystallite_Li0, & !< intermediate velocitiy grad at start of FE inc
crystallite_partionedLi0,& !< intermediate velocity grad at start of homog inc crystallite_partionedLi0,& !< intermediate velocity grad at start of homog inc
crystallite_Fe, & !< current "elastic" def grad (end of converged time step) crystallite_Fe, & !< current "elastic" def grad (end of converged time step)
crystallite_P, & !< 1st Piola-Kirchhoff stress per grain crystallite_P !< 1st Piola-Kirchhoff stress per grain
crystallite_subF !< def grad to be reached at end of crystallite inc
real(pReal), dimension(:,:,:,:,:), allocatable, private :: & real(pReal), dimension(:,:,:,:,:), allocatable, private :: &
crystallite_subFe0,& !< "elastic" def grad at start of crystallite inc crystallite_subFe0,& !< "elastic" def grad at start of crystallite inc
crystallite_invFp, & !< inverse of current plastic def grad (end of converged time step) crystallite_invFp, & !< inverse of current plastic def grad (end of converged time step)
crystallite_subFp0,& !< plastic def grad at start of crystallite inc crystallite_subFp0,& !< plastic def grad at start of crystallite inc
crystallite_invFi, & !< inverse of current intermediate def grad (end of converged time step) crystallite_invFi, & !< inverse of current intermediate def grad (end of converged time step)
crystallite_subFi0,& !< intermediate def grad at start of crystallite inc crystallite_subFi0,& !< intermediate def grad at start of crystallite inc
crystallite_subF, & !< def grad to be reached at end of crystallite inc
crystallite_subF0, & !< def grad at start of crystallite inc crystallite_subF0, & !< def grad at start of crystallite inc
crystallite_subLp0,& !< plastic velocity grad at start of crystallite inc crystallite_subLp0,& !< plastic velocity grad at start of crystallite inc
crystallite_subLi0,& !< intermediate velocity grad at start of crystallite inc crystallite_subLi0,& !< intermediate velocity grad at start of crystallite inc
@ -193,7 +193,7 @@ subroutine crystallite_init
c, & !< counter in integration point component loop c, & !< counter in integration point component loop
i, & !< counter in integration point loop i, & !< counter in integration point loop
e, & !< counter in element loop e, & !< counter in element loop
o, & !< counter in output loop o = 0_pInt, & !< counter in output loop
r, & !< counter in crystallite loop r, & !< counter in crystallite loop
cMax, & !< maximum number of integration point components cMax, & !< maximum number of integration point components
iMax, & !< maximum number of integration points iMax, & !< maximum number of integration points
@ -1239,14 +1239,16 @@ subroutine crystallite_integrateStateRK4()
use numerics, only: & use numerics, only: &
numerics_integrationMode numerics_integrationMode
use debug, only: & use debug, only: &
#ifdef DEBUG
debug_e, &
debug_i, &
debug_g, &
#endif
debug_level, & debug_level, &
debug_crystallite, & debug_crystallite, &
debug_levelBasic, & debug_levelBasic, &
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective, & debug_levelSelective, &
debug_e, &
debug_i, &
debug_g, &
debug_StateLoopDistribution debug_StateLoopDistribution
use FEsolving, only: & use FEsolving, only: &
FEsolving_execElem, & FEsolving_execElem, &
@ -1533,14 +1535,16 @@ subroutine crystallite_integrateStateRKCK45()
use, intrinsic :: & use, intrinsic :: &
IEEE_arithmetic IEEE_arithmetic
use debug, only: & use debug, only: &
#ifdef DEBUG
debug_e, &
debug_i, &
debug_g, &
#endif
debug_level, & debug_level, &
debug_crystallite, & debug_crystallite, &
debug_levelBasic, & debug_levelBasic, &
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective, & debug_levelSelective, &
debug_e, &
debug_i, &
debug_g, &
debug_StateLoopDistribution debug_StateLoopDistribution
use numerics, only: & use numerics, only: &
rTol_crystalliteState, & rTol_crystalliteState, &
@ -2036,14 +2040,16 @@ subroutine crystallite_integrateStateAdaptiveEuler()
use, intrinsic :: & use, intrinsic :: &
IEEE_arithmetic IEEE_arithmetic
use debug, only: & use debug, only: &
#ifdef DEBUG
debug_e, &
debug_i, &
debug_g, &
#endif
debug_level, & debug_level, &
debug_crystallite, & debug_crystallite, &
debug_levelBasic, & debug_levelBasic, &
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective, & debug_levelSelective, &
debug_e, &
debug_i, &
debug_g, &
debug_StateLoopDistribution debug_StateLoopDistribution
use numerics, only: & use numerics, only: &
rTol_crystalliteState, & rTol_crystalliteState, &
@ -2396,14 +2402,16 @@ subroutine crystallite_integrateStateEuler()
use, intrinsic :: & use, intrinsic :: &
IEEE_arithmetic IEEE_arithmetic
use debug, only: & use debug, only: &
#ifdef DEBUG
debug_e, &
debug_i, &
debug_g, &
#endif
debug_level, & debug_level, &
debug_crystallite, & debug_crystallite, &
debug_levelBasic, & debug_levelBasic, &
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective, & debug_levelSelective, &
debug_e, &
debug_i, &
debug_g, &
debug_StateLoopDistribution debug_StateLoopDistribution
use numerics, only: & use numerics, only: &
numerics_integrationMode, & numerics_integrationMode, &
@ -2619,9 +2627,11 @@ subroutine crystallite_integrateStateFPI()
use, intrinsic :: & use, intrinsic :: &
IEEE_arithmetic IEEE_arithmetic
use debug, only: & use debug, only: &
#ifdef DEBUG
debug_e, & debug_e, &
debug_i, & debug_i, &
debug_g, & debug_g, &
#endif
debug_level,& debug_level,&
debug_crystallite, & debug_crystallite, &
debug_levelBasic, & debug_levelBasic, &
@ -3068,14 +3078,16 @@ logical function crystallite_stateJump(ipc,ip,el)
IEEE_arithmetic IEEE_arithmetic
use prec, only: & use prec, only: &
dNeq0 dNeq0
#ifdef DEBUG
use debug, only: & use debug, only: &
debug_e, &
debug_i, &
debug_g, &
debug_level, & debug_level, &
debug_crystallite, & debug_crystallite, &
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective, & debug_levelSelective
debug_e, & #endif
debug_i, &
debug_g
use material, only: & use material, only: &
plasticState, & plasticState, &
sourceState, & sourceState, &
@ -3205,9 +3217,11 @@ logical function crystallite_integrateStress(&
debug_levelBasic, & debug_levelBasic, &
debug_levelExtensive, & debug_levelExtensive, &
debug_levelSelective, & debug_levelSelective, &
#ifdef DEBUG
debug_e, & debug_e, &
debug_i, & debug_i, &
debug_g, & debug_g, &
#endif
debug_cumLpCalls, & debug_cumLpCalls, &
debug_cumLpTicks, & debug_cumLpTicks, &
debug_StressLoopLpDistribution, & debug_StressLoopLpDistribution, &
@ -3233,7 +3247,9 @@ logical function crystallite_integrateStress(&
math_Plain33to9, & math_Plain33to9, &
math_Plain9to33, & math_Plain9to33, &
math_Plain99to3333 math_Plain99to3333
#ifdef DEBUG
use mesh, only: mesh_element use mesh, only: mesh_element
#endif
implicit none implicit none
integer(pInt), intent(in):: el, & ! element index integer(pInt), intent(in):: el, & ! element index
@ -3297,8 +3313,8 @@ logical function crystallite_integrateStress(&
p, & p, &
jacoCounterLp, & jacoCounterLp, &
jacoCounterLi ! counters to check for Jacobian update jacoCounterLi ! counters to check for Jacobian update
integer(pLongInt) tick, & integer(pLongInt) :: tick = 0_pLongInt, &
tock, & tock = 0_pLongInt, &
tickrate, & tickrate, &
maxticks maxticks

View File

@ -128,7 +128,7 @@ subroutine homogenization_init
integer(pInt), dimension(:) , pointer :: thisNoutput integer(pInt), dimension(:) , pointer :: thisNoutput
character(len=64), dimension(:,:), pointer :: thisOutput character(len=64), dimension(:,:), pointer :: thisOutput
character(len=32) :: outputName !< name of output, intermediate fix until HDF5 output is ready character(len=32) :: outputName !< name of output, intermediate fix until HDF5 output is ready
logical :: knownHomogenization, knownThermal, knownDamage, knownVacancyflux, knownPorosity, knownHydrogenflux logical :: valid
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -199,7 +199,7 @@ subroutine homogenization_init
do p = 1,material_Nhomogenization do p = 1,material_Nhomogenization
if (any(material_homog == p)) then if (any(material_homog == p)) then
i = homogenization_typeInstance(p) ! which instance of this homogenization type i = homogenization_typeInstance(p) ! which instance of this homogenization type
knownHomogenization = .true. ! assume valid valid = .true. ! assume valid
select case(homogenization_type(p)) ! split per homogenization type select case(homogenization_type(p)) ! split per homogenization type
case (HOMOGENIZATION_NONE_ID) case (HOMOGENIZATION_NONE_ID)
outputName = HOMOGENIZATION_NONE_label outputName = HOMOGENIZATION_NONE_label
@ -217,10 +217,10 @@ subroutine homogenization_init
thisOutput => homogenization_RGC_output thisOutput => homogenization_RGC_output
thisSize => homogenization_RGC_sizePostResult thisSize => homogenization_RGC_sizePostResult
case default case default
knownHomogenization = .false. valid = .false.
end select end select
write(FILEUNIT,'(/,a,/)') '['//trim(homogenization_name(p))//']' write(FILEUNIT,'(/,a,/)') '['//trim(homogenization_name(p))//']'
if (knownHomogenization) then if (valid) then
write(FILEUNIT,'(a)') '(type)'//char(9)//trim(outputName) write(FILEUNIT,'(a)') '(type)'//char(9)//trim(outputName)
write(FILEUNIT,'(a,i4)') '(ngrains)'//char(9),homogenization_Ngrains(p) write(FILEUNIT,'(a,i4)') '(ngrains)'//char(9),homogenization_Ngrains(p)
if (homogenization_type(p) /= HOMOGENIZATION_NONE_ID) then if (homogenization_type(p) /= HOMOGENIZATION_NONE_ID) then
@ -230,7 +230,7 @@ subroutine homogenization_init
endif endif
endif endif
i = thermal_typeInstance(p) ! which instance of this thermal type i = thermal_typeInstance(p) ! which instance of this thermal type
knownThermal = .true. ! assume valid valid = .true. ! assume valid
select case(thermal_type(p)) ! split per thermal type select case(thermal_type(p)) ! split per thermal type
case (THERMAL_isothermal_ID) case (THERMAL_isothermal_ID)
outputName = THERMAL_isothermal_label outputName = THERMAL_isothermal_label
@ -248,9 +248,9 @@ subroutine homogenization_init
thisOutput => thermal_conduction_output thisOutput => thermal_conduction_output
thisSize => thermal_conduction_sizePostResult thisSize => thermal_conduction_sizePostResult
case default case default
knownThermal = .false. valid = .false.
end select end select
if (knownThermal) then if (valid) then
write(FILEUNIT,'(a)') '(thermal)'//char(9)//trim(outputName) write(FILEUNIT,'(a)') '(thermal)'//char(9)//trim(outputName)
if (thermal_type(p) /= THERMAL_isothermal_ID) then if (thermal_type(p) /= THERMAL_isothermal_ID) then
do e = 1,thisNoutput(i) do e = 1,thisNoutput(i)
@ -259,7 +259,7 @@ subroutine homogenization_init
endif endif
endif endif
i = damage_typeInstance(p) ! which instance of this damage type i = damage_typeInstance(p) ! which instance of this damage type
knownDamage = .true. ! assume valid valid = .true. ! assume valid
select case(damage_type(p)) ! split per damage type select case(damage_type(p)) ! split per damage type
case (DAMAGE_none_ID) case (DAMAGE_none_ID)
outputName = DAMAGE_none_label outputName = DAMAGE_none_label
@ -277,9 +277,9 @@ subroutine homogenization_init
thisOutput => damage_nonlocal_output thisOutput => damage_nonlocal_output
thisSize => damage_nonlocal_sizePostResult thisSize => damage_nonlocal_sizePostResult
case default case default
knownDamage = .false. valid = .false.
end select end select
if (knownDamage) then if (valid) then
write(FILEUNIT,'(a)') '(damage)'//char(9)//trim(outputName) write(FILEUNIT,'(a)') '(damage)'//char(9)//trim(outputName)
if (damage_type(p) /= DAMAGE_none_ID) then if (damage_type(p) /= DAMAGE_none_ID) then
do e = 1,thisNoutput(i) do e = 1,thisNoutput(i)
@ -288,7 +288,7 @@ subroutine homogenization_init
endif endif
endif endif
i = vacancyflux_typeInstance(p) ! which instance of this vacancy flux type i = vacancyflux_typeInstance(p) ! which instance of this vacancy flux type
knownVacancyflux = .true. ! assume valid valid = .true. ! assume valid
select case(vacancyflux_type(p)) ! split per vacancy flux type select case(vacancyflux_type(p)) ! split per vacancy flux type
case (VACANCYFLUX_isoconc_ID) case (VACANCYFLUX_isoconc_ID)
outputName = VACANCYFLUX_isoconc_label outputName = VACANCYFLUX_isoconc_label
@ -306,9 +306,9 @@ subroutine homogenization_init
thisOutput => vacancyflux_cahnhilliard_output thisOutput => vacancyflux_cahnhilliard_output
thisSize => vacancyflux_cahnhilliard_sizePostResult thisSize => vacancyflux_cahnhilliard_sizePostResult
case default case default
knownVacancyflux = .false. valid = .false.
end select end select
if (knownVacancyflux) then if (valid) then
write(FILEUNIT,'(a)') '(vacancyflux)'//char(9)//trim(outputName) write(FILEUNIT,'(a)') '(vacancyflux)'//char(9)//trim(outputName)
if (vacancyflux_type(p) /= VACANCYFLUX_isoconc_ID) then if (vacancyflux_type(p) /= VACANCYFLUX_isoconc_ID) then
do e = 1,thisNoutput(i) do e = 1,thisNoutput(i)
@ -317,7 +317,7 @@ subroutine homogenization_init
endif endif
endif endif
i = porosity_typeInstance(p) ! which instance of this porosity type i = porosity_typeInstance(p) ! which instance of this porosity type
knownPorosity = .true. ! assume valid valid = .true. ! assume valid
select case(porosity_type(p)) ! split per porosity type select case(porosity_type(p)) ! split per porosity type
case (POROSITY_none_ID) case (POROSITY_none_ID)
outputName = POROSITY_none_label outputName = POROSITY_none_label
@ -330,9 +330,9 @@ subroutine homogenization_init
thisOutput => porosity_phasefield_output thisOutput => porosity_phasefield_output
thisSize => porosity_phasefield_sizePostResult thisSize => porosity_phasefield_sizePostResult
case default case default
knownPorosity = .false. valid = .false.
end select end select
if (knownPorosity) then if (valid) then
write(FILEUNIT,'(a)') '(porosity)'//char(9)//trim(outputName) write(FILEUNIT,'(a)') '(porosity)'//char(9)//trim(outputName)
if (porosity_type(p) /= POROSITY_none_ID) then if (porosity_type(p) /= POROSITY_none_ID) then
do e = 1,thisNoutput(i) do e = 1,thisNoutput(i)
@ -341,7 +341,7 @@ subroutine homogenization_init
endif endif
endif endif
i = hydrogenflux_typeInstance(p) ! which instance of this hydrogen flux type i = hydrogenflux_typeInstance(p) ! which instance of this hydrogen flux type
knownHydrogenflux = .true. ! assume valid valid = .true. ! assume valid
select case(hydrogenflux_type(p)) ! split per hydrogen flux type select case(hydrogenflux_type(p)) ! split per hydrogen flux type
case (HYDROGENFLUX_isoconc_ID) case (HYDROGENFLUX_isoconc_ID)
outputName = HYDROGENFLUX_isoconc_label outputName = HYDROGENFLUX_isoconc_label
@ -354,9 +354,9 @@ subroutine homogenization_init
thisOutput => hydrogenflux_cahnhilliard_output thisOutput => hydrogenflux_cahnhilliard_output
thisSize => hydrogenflux_cahnhilliard_sizePostResult thisSize => hydrogenflux_cahnhilliard_sizePostResult
case default case default
knownHydrogenflux = .false. valid = .false.
end select end select
if (knownHydrogenflux) then if (valid) then
write(FILEUNIT,'(a)') '(hydrogenflux)'//char(9)//trim(outputName) write(FILEUNIT,'(a)') '(hydrogenflux)'//char(9)//trim(outputName)
if (hydrogenflux_type(p) /= HYDROGENFLUX_isoconc_ID) then if (hydrogenflux_type(p) /= HYDROGENFLUX_isoconc_ID) then
do e = 1,thisNoutput(i) do e = 1,thisNoutput(i)

View File

@ -379,30 +379,30 @@ module mesh
],pInt) ],pInt)
integer(pInt), dimension(FE_Nelemtypes), parameter, private :: MESH_VTKELEMTYPE = & ! integer(pInt), dimension(FE_Nelemtypes), parameter, private :: MESH_VTKELEMTYPE = &
int([ & ! int([ &
5, & ! element 6 (2D 3node 1ip) ! 5, & ! element 6 (2D 3node 1ip)
22, & ! element 125 (2D 6node 3ip) ! 22, & ! element 125 (2D 6node 3ip)
9, & ! element 11 (2D 4node 4ip) ! 9, & ! element 11 (2D 4node 4ip)
23, & ! element 27 (2D 8node 9ip) ! 23, & ! element 27 (2D 8node 9ip)
23, & ! element 54 (2D 8node 4ip) ! 23, & ! element 54 (2D 8node 4ip)
10, & ! element 134 (3D 4node 1ip) ! 10, & ! element 134 (3D 4node 1ip)
10, & ! element 157 (3D 5node 4ip) ! 10, & ! element 157 (3D 5node 4ip)
24, & ! element 127 (3D 10node 4ip) ! 24, & ! element 127 (3D 10node 4ip)
13, & ! element 136 (3D 6node 6ip) ! 13, & ! element 136 (3D 6node 6ip)
12, & ! element 117 (3D 8node 1ip) ! 12, & ! element 117 (3D 8node 1ip)
12, & ! element 7 (3D 8node 8ip) ! 12, & ! element 7 (3D 8node 8ip)
25, & ! element 57 (3D 20node 8ip) ! 25, & ! element 57 (3D 20node 8ip)
25 & ! element 21 (3D 20node 27ip) ! 25 & ! element 21 (3D 20node 27ip)
],pInt) ! ],pInt)
!
integer(pInt), dimension(FE_Ncelltypes), parameter, private :: MESH_VTKCELLTYPE = & ! integer(pInt), dimension(FE_Ncelltypes), parameter, private :: MESH_VTKCELLTYPE = &
int([ & ! int([ &
5, & ! (2D 3node) ! 5, & ! (2D 3node)
9, & ! (2D 4node) ! 9, & ! (2D 4node)
10, & ! (3D 4node) ! 10, & ! (3D 4node)
12 & ! (3D 8node) ! 12 & ! (3D 8node)
],pInt) ! ],pInt)
public :: & public :: &
@ -2848,16 +2848,18 @@ use IO, only: &
implicit none implicit none
integer(pInt), intent(in) :: fileUnit integer(pInt), intent(in) :: fileUnit
#ifndef Spectral #ifdef Spectral
mesh_periodicSurface = .true.
end subroutine mesh_get_damaskOptions
#else
integer(pInt), allocatable, dimension(:) :: chunkPos integer(pInt), allocatable, dimension(:) :: chunkPos
integer(pInt) chunk, Nchunks integer(pInt) chunk, Nchunks
character(len=300) :: line, damaskOption, v character(len=300) :: line, damaskOption, v
character(len=300) :: keyword character(len=300) :: keyword
#endif
#ifdef Spectral
mesh_periodicSurface = .true.
#else
mesh_periodicSurface = .false. mesh_periodicSurface = .false.
#ifdef Marc4DAMASK #ifdef Marc4DAMASK
keyword = '$damask' keyword = '$damask'
@ -2886,9 +2888,9 @@ use IO, only: &
enddo enddo
610 FORMAT(A300) 610 FORMAT(A300)
#endif
620 end subroutine mesh_get_damaskOptions 620 end subroutine mesh_get_damaskOptions
#endif
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------

View File

@ -120,9 +120,9 @@ module numerics
petsc_options = '' petsc_options = ''
integer(pInt), protected, public :: & integer(pInt), protected, public :: &
fftw_planner_flag = 32_pInt, & !< conversion of fftw_plan_mode to integer, basically what is usually done in the include file of fftw fftw_planner_flag = 32_pInt, & !< conversion of fftw_plan_mode to integer, basically what is usually done in the include file of fftw
continueCalculation = 0_pInt, & !< 0: exit if BVP solver does not converge, 1: continue calculation if BVP solver does not converge
divergence_correction = 2_pInt !< correct divergence calculation in fourier space 0: no correction, 1: size scaled to 1, 2: size scaled to Npoints divergence_correction = 2_pInt !< correct divergence calculation in fourier space 0: no correction, 1: size scaled to 1, 2: size scaled to Npoints
logical, protected, public :: & logical, protected, public :: &
continueCalculation = .false., & !< false:exit if BVP solver does not converge, true: continue calculation despite BVP solver not converging
memory_efficient = .true., & !< for fast execution (pre calculation of gamma_hat), Default .true.: do not precalculate memory_efficient = .true., & !< for fast execution (pre calculation of gamma_hat), Default .true.: do not precalculate
update_gamma = .false. !< update gamma operator with current stiffness, Default .false.: use initial stiffness update_gamma = .false. !< update gamma operator with current stiffness, Default .false.: use initial stiffness
#endif #endif
@ -424,7 +424,7 @@ subroutine numerics_init
case ('err_stress_tolabs') case ('err_stress_tolabs')
err_stress_tolabs = IO_floatValue(line,chunkPos,2_pInt) err_stress_tolabs = IO_floatValue(line,chunkPos,2_pInt)
case ('continuecalculation') case ('continuecalculation')
continueCalculation = IO_intValue(line,chunkPos,2_pInt) continueCalculation = IO_intValue(line,chunkPos,2_pInt) > 0_pInt
case ('memory_efficient') case ('memory_efficient')
memory_efficient = IO_intValue(line,chunkPos,2_pInt) > 0_pInt memory_efficient = IO_intValue(line,chunkPos,2_pInt) > 0_pInt
case ('fftw_timelimit') case ('fftw_timelimit')
@ -599,7 +599,7 @@ subroutine numerics_init
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! spectral parameters ! spectral parameters
#ifdef Spectral #ifdef Spectral
write(6,'(a24,1x,i8)') ' continueCalculation: ',continueCalculation write(6,'(a24,1x,L8)') ' continueCalculation: ',continueCalculation
write(6,'(a24,1x,L8)') ' memory_efficient: ',memory_efficient write(6,'(a24,1x,L8)') ' memory_efficient: ',memory_efficient
write(6,'(a24,1x,i8)') ' divergence_correction: ',divergence_correction write(6,'(a24,1x,i8)') ' divergence_correction: ',divergence_correction
write(6,'(a24,1x,a)') ' spectral_derivative: ',trim(spectral_derivative) write(6,'(a24,1x,a)') ' spectral_derivative: ',trim(spectral_derivative)
@ -698,8 +698,6 @@ subroutine numerics_init
if (err_hydrogenflux_tolabs <= 0.0_pReal) call IO_error(301_pInt,ext_msg='err_hydrogenflux_tolabs') if (err_hydrogenflux_tolabs <= 0.0_pReal) call IO_error(301_pInt,ext_msg='err_hydrogenflux_tolabs')
if (err_hydrogenflux_tolrel <= 0.0_pReal) call IO_error(301_pInt,ext_msg='err_hydrogenflux_tolrel') if (err_hydrogenflux_tolrel <= 0.0_pReal) call IO_error(301_pInt,ext_msg='err_hydrogenflux_tolrel')
#ifdef Spectral #ifdef Spectral
if (continueCalculation /= 0_pInt .and. &
continueCalculation /= 1_pInt) call IO_error(301_pInt,ext_msg='continueCalculation')
if (divergence_correction < 0_pInt .or. & if (divergence_correction < 0_pInt .or. &
divergence_correction > 2_pInt) call IO_error(301_pInt,ext_msg='divergence_correction') divergence_correction > 2_pInt) call IO_error(301_pInt,ext_msg='divergence_correction')
if (update_gamma .and. & if (update_gamma .and. &

View File

@ -15,7 +15,7 @@ module DAMASK_interface
private private
#include <petsc/finclude/petscsys.h> #include <petsc/finclude/petscsys.h>
logical, public, protected :: appendToOutFile = .false. !< Append to existing spectralOut file (in case of restart, not in case of regridding) logical, public, protected :: appendToOutFile = .false. !< Append to existing spectralOut file (in case of restart, not in case of regridding)
integer(pInt), public, protected :: spectralRestartInc = 1_pInt !< Increment at which calculation starts integer(pInt), public, protected :: spectralRestartInc = 0_pInt !< Increment at which calculation starts
character(len=1024), public, protected :: & character(len=1024), public, protected :: &
geometryFile = '', & !< parameter given for geometry file geometryFile = '', & !< parameter given for geometry file
loadCaseFile = '' !< parameter given for load case file loadCaseFile = '' !< parameter given for load case file
@ -167,12 +167,12 @@ subroutine DAMASK_interface_init()
write(6,'(a)') ' For further configuration place "numerics.config"' write(6,'(a)') ' For further configuration place "numerics.config"'
write(6,'(a)')' and "debug.config" in that directory.' write(6,'(a)')' and "debug.config" in that directory.'
write(6,'(/,a)')' --restart XX' write(6,'(/,a)')' --restart XX'
write(6,'(a)') ' Reads in total increment No. XX-1 and continues to' write(6,'(a)') ' Reads in increment XX and continues with calculating'
write(6,'(a)') ' calculate total increment No. XX.' write(6,'(a)') ' increment XX+1 based on this.'
write(6,'(a)') ' Appends to existing results file ' write(6,'(a)') ' Appends to existing results file'
write(6,'(a)') ' "NameOfGeom_NameOfLoadFile.spectralOut".' write(6,'(a)') ' "NameOfGeom_NameOfLoadFile.spectralOut".'
write(6,'(a)') ' Works only if the restart information for total increment' write(6,'(a)') ' Works only if the restart information for increment XX'
write(6,'(a)') ' No. XX-1 is available in the working directory.' write(6,'(a)') ' is available in the working directory.'
write(6,'(/,a)')' -----------------------------------------------------------------------' write(6,'(/,a)')' -----------------------------------------------------------------------'
write(6,'(a)') ' Help:' write(6,'(a)') ' Help:'
write(6,'(/,a)')' --help' write(6,'(/,a)')' --help'
@ -204,7 +204,7 @@ subroutine DAMASK_interface_init()
write(6,'(a,a)') ' Host name: ', trim(hostName) write(6,'(a,a)') ' Host name: ', trim(hostName)
write(6,'(a,a)') ' User name: ', trim(userName) write(6,'(a,a)') ' User name: ', trim(userName)
write(6,'(a,a)') ' Command line call: ', trim(commandLine) write(6,'(a,a)') ' Command line call: ', trim(commandLine)
if (len(trim(workingDirArg))>0) & if (len(trim(workingDirArg)) > 0) &
write(6,'(a,a)') ' Working dir argument: ', trim(workingDirArg) write(6,'(a,a)') ' Working dir argument: ', trim(workingDirArg)
write(6,'(a,a)') ' Geometry argument: ', trim(geometryArg) write(6,'(a,a)') ' Geometry argument: ', trim(geometryArg)
write(6,'(a,a)') ' Loadcase argument: ', trim(loadcaseArg) write(6,'(a,a)') ' Loadcase argument: ', trim(loadcaseArg)
@ -212,8 +212,8 @@ subroutine DAMASK_interface_init()
write(6,'(a,a)') ' Geometry file: ', trim(geometryFile) write(6,'(a,a)') ' Geometry file: ', trim(geometryFile)
write(6,'(a,a)') ' Loadcase file: ', trim(loadCaseFile) write(6,'(a,a)') ' Loadcase file: ', trim(loadCaseFile)
write(6,'(a,a)') ' Solver job name: ', trim(getSolverJobName()) write(6,'(a,a)') ' Solver job name: ', trim(getSolverJobName())
if (SpectralRestartInc > 1_pInt) & if (SpectralRestartInc > 0_pInt) &
write(6,'(a,i6.6)') ' Restart at increment: ', spectralRestartInc write(6,'(a,i6.6)') ' Restart from increment: ', spectralRestartInc
write(6,'(a,l1,/)') ' Append to result file: ', appendToOutFile write(6,'(a,l1,/)') ' Append to result file: ', appendToOutFile
end subroutine DAMASK_interface_init end subroutine DAMASK_interface_init

View File

@ -43,17 +43,20 @@ module spectral_mech_AL
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! stress, stiffness and compliance average etc. ! stress, stiffness and compliance average etc.
real(pReal), private, dimension(3,3) :: & real(pReal), private, dimension(3,3) :: &
F_aimDot, & !< assumed rate of average deformation gradient F_aimDot = 0.0_pReal, & !< assumed rate of average deformation gradient
F_aim = math_I3, & !< current prescribed deformation gradient F_aim = math_I3, & !< current prescribed deformation gradient
F_aim_lastInc = math_I3, & !< previous average deformation gradient F_aim_lastInc = math_I3, & !< previous average deformation gradient
F_av = 0.0_pReal, & !< average incompatible def grad field F_av = 0.0_pReal, & !< average incompatible def grad field
P_av = 0.0_pReal, & !< average 1st Piola--Kirchhoff stress P_av = 0.0_pReal, & !< average 1st Piola--Kirchhoff stress
P_avLastEval = 0.0_pReal !< average 1st Piola--Kirchhoff stress last call of CPFEM_general P_avLastEval = 0.0_pReal !< average 1st Piola--Kirchhoff stress last call of CPFEM_general
character(len=1024), private :: incInfo !< time and increment information character(len=1024), private :: incInfo !< time and increment information
real(pReal), private, dimension(3,3,3,3) :: & real(pReal), private, dimension(3,3,3,3) :: &
C_volAvg = 0.0_pReal, & !< current volume average stiffness C_volAvg = 0.0_pReal, & !< current volume average stiffness
C_volAvgLastInc = 0.0_pReal, & !< previous volume average stiffness C_volAvgLastInc = 0.0_pReal, & !< previous volume average stiffness
C_minMaxAvg = 0.0_pReal, & !< current (min+max)/2 stiffness C_minMaxAvg = 0.0_pReal, & !< current (min+max)/2 stiffness
C_minMaxAvgLastInc = 0.0_pReal, & !< previous (min+max)/2 stiffness
S = 0.0_pReal, & !< current compliance (filled up with zeros) S = 0.0_pReal, & !< current compliance (filled up with zeros)
C_scale = 0.0_pReal, & C_scale = 0.0_pReal, &
S_scale = 0.0_pReal S_scale = 0.0_pReal
@ -62,7 +65,7 @@ module spectral_mech_AL
err_BC, & !< deviation from stress BC err_BC, & !< deviation from stress BC
err_curl, & !< RMS of curl of F err_curl, & !< RMS of curl of F
err_div !< RMS of div of P err_div !< RMS of div of P
logical, private :: ForwardData
integer(pInt), private :: & integer(pInt), private :: &
totalIter = 0_pInt !< total iteration in current increment totalIter = 0_pInt !< total iteration in current increment
@ -80,7 +83,7 @@ module spectral_mech_AL
contains contains
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief allocates all neccessary fields and fills them with data, potentially from restart info !> @brief allocates all necessary fields and fills them with data, potentially from restart info
!> @todo use sourced allocation, e.g. allocate(Fdot,source = F_lastInc) !> @todo use sourced allocation, e.g. allocate(Fdot,source = F_lastInc)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine AL_init subroutine AL_init
@ -102,12 +105,15 @@ subroutine AL_init
use numerics, only: & use numerics, only: &
worldrank, & worldrank, &
worldsize worldsize
use homogenization, only: &
materialpoint_F0
use DAMASK_interface, only: & use DAMASK_interface, only: &
getSolverJobName getSolverJobName
use spectral_utilities, only: & use spectral_utilities, only: &
Utilities_constitutiveResponse, & Utilities_constitutiveResponse, &
Utilities_updateGamma, & Utilities_updateGamma, &
Utilities_updateIPcoords Utilities_updateIPcoords, &
wgt
use mesh, only: & use mesh, only: &
grid, & grid, &
grid3 grid3
@ -120,7 +126,11 @@ subroutine AL_init
temp33_Real = 0.0_pReal temp33_Real = 0.0_pReal
PetscErrorCode :: ierr PetscErrorCode :: ierr
PetscScalar, pointer, dimension(:,:,:,:) :: xx_psc, F, F_lambda PetscScalar, pointer, dimension(:,:,:,:) :: &
FandF_lambda, & ! overall pointer to solution data
F, & ! specific (sub)pointer
F_lambda ! specific (sub)pointer
integer(pInt), dimension(:), allocatable :: localK integer(pInt), dimension(:), allocatable :: localK
integer(pInt) :: proc integer(pInt) :: proc
character(len=1024) :: rankStr character(len=1024) :: rankStr
@ -164,78 +174,70 @@ subroutine AL_init
grid(1),grid(2),localK, & ! local grid grid(1),grid(2),localK, & ! local grid
da,ierr) ! handle, error da,ierr) ! handle, error
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) ! connect snes to da
call DMCreateGlobalVector(da,solution_vec,ierr); CHKERRQ(ierr) call DMCreateGlobalVector(da,solution_vec,ierr); CHKERRQ(ierr) ! global solution vector (grid x 9, i.e. every def grad tensor)
call DMDASNESSetFunctionLocal(da,INSERT_VALUES,AL_formResidual,PETSC_NULL_OBJECT,ierr) call DMDASNESSetFunctionLocal(da,INSERT_VALUES,AL_formResidual,PETSC_NULL_OBJECT,ierr) ! residual vector of same shape as solution vector
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetConvergenceTest(snes,AL_converged,PETSC_NULL_OBJECT,PETSC_NULL_FUNCTION,ierr) call SNESSetConvergenceTest(snes,AL_converged,PETSC_NULL_OBJECT,PETSC_NULL_FUNCTION,ierr) ! specify custom convergence check function "_converged"
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetFromOptions(snes,ierr); CHKERRQ(ierr) call SNESSetFromOptions(snes,ierr); CHKERRQ(ierr) ! pull it all together with additional cli arguments
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! init fields ! init fields
call DMDAVecGetArrayF90(da,solution_vec,xx_psc,ierr); CHKERRQ(ierr) ! places pointer xx_psc on PETSc data call DMDAVecGetArrayF90(da,solution_vec,FandF_lambda,ierr); CHKERRQ(ierr) ! places pointer on PETSc data
F => xx_psc(0:8,:,:,:) F => FandF_lambda( 0: 8,:,:,:)
F_lambda => xx_psc(9:17,:,:,:) F_lambda => FandF_lambda( 9:17,:,:,:)
restart: if (restartInc > 1_pInt) then
if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0 .and. worldrank == 0_pInt) & restart: if (restartInc > 0_pInt) then
write(6,'(/,a,'//IO_intOut(restartInc-1_pInt)//',a)') & if (iand(debug_level(debug_spectral),debug_spectralRestart) /= 0) then
'reading values of increment ', restartInc - 1_pInt, ' from file' write(6,'(/,a,'//IO_intOut(restartInc)//',a)') &
'reading values of increment ', restartInc, ' from file'
flush(6) flush(6)
endif
write(rankStr,'(a1,i0)')'_',worldrank write(rankStr,'(a1,i0)')'_',worldrank
call IO_read_realFile(777,'F'//trim(rankStr),trim(getSolverJobName()),size(F)) call IO_read_realFile(777,'F'//trim(rankStr),trim(getSolverJobName()),size(F))
read (777,rec=1) F read (777,rec=1) F; close (777)
close (777)
call IO_read_realFile(777,'F_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lastInc)) call IO_read_realFile(777,'F_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lastInc))
read (777,rec=1) F_lastInc read (777,rec=1) F_lastInc; close (777)
close (777)
call IO_read_realFile(777,'F_lambda'//trim(rankStr),trim(getSolverJobName()),size(F_lambda)) call IO_read_realFile(777,'F_lambda'//trim(rankStr),trim(getSolverJobName()),size(F_lambda))
read (777,rec=1) F_lambda read (777,rec=1) F_lambda; close (777)
close (777) call IO_read_realFile(777,'F_lambda_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lambda_lastInc))
call IO_read_realFile(777,'F_lambda_lastInc'//trim(rankStr),& read (777,rec=1) F_lambda_lastInc; close (777)
trim(getSolverJobName()),size(F_lambda_lastInc)) call IO_read_realFile(777,'F_aimDot',trim(getSolverJobName()),size(F_aimDot))
read (777,rec=1) F_lambda_lastInc read (777,rec=1) F_aimDot; close (777)
close (777) F_aim = reshape(sum(sum(sum(F,dim=4),dim=3),dim=2) * wgt, [3,3]) ! average of F
call IO_read_realFile(777,'F_aim', trim(getSolverJobName()),size(F_aim)) F_aim_lastInc = sum(sum(sum(F_lastInc,dim=5),dim=4),dim=3) * wgt ! average of F_lastInc
read (777,rec=1) F_aim elseif (restartInc == 0_pInt) then restart
close (777)
call IO_read_realFile(777,'F_aim_lastInc', trim(getSolverJobName()),size(F_aim_lastInc))
read (777,rec=1) F_aim_lastInc
close (777)
call IO_read_realFile(777,'F_aimDot',trim(getSolverJobName()),size(f_aimDot))
read (777,rec=1) f_aimDot
close (777)
elseif (restartInc == 1_pInt) then restart
F_lastInc = spread(spread(spread(math_I3,3,grid(1)),4,grid(2)),5,grid3) ! initialize to identity F_lastInc = spread(spread(spread(math_I3,3,grid(1)),4,grid(2)),5,grid3) ! initialize to identity
F = reshape(F_lastInc,[9,grid(1),grid(2),grid3]) F = reshape(F_lastInc,[9,grid(1),grid(2),grid3])
F_lambda = F F_lambda = F
F_lambda_lastInc = F_lastInc F_lambda_lastInc = F_lastInc
endif restart endif restart
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3]) ! set starting condition for materialpoint_stressAndItsTangent
call Utilities_updateIPcoords(reshape(F,shape(F_lastInc))) call Utilities_updateIPcoords(reshape(F,shape(F_lastInc)))
call Utilities_constitutiveResponse(F_lastInc, reshape(F,shape(F_lastInc)), & call Utilities_constitutiveResponse(P,temp33_Real,C_volAvg,C_minMaxAvg, & ! stress field, stress avg, global average of stiffness and (min+max)/2
0.0_pReal,P,C_volAvg,C_minMaxAvg,temp33_Real,.false.,math_I3) reshape(F,shape(F_lastInc)), & ! target F
0.0_pReal, & ! time increment
math_I3) ! no rotation of boundary condition
nullify(F) nullify(F)
nullify(F_lambda) nullify(F_lambda)
call DMDAVecRestoreArrayF90(da,solution_vec,xx_psc,ierr); CHKERRQ(ierr) ! write data back to PETSc call DMDAVecRestoreArrayF90(da,solution_vec,FandF_lambda,ierr); CHKERRQ(ierr) ! write data back to PETSc
restartRead: if (restartInc > 1_pInt) then restartRead: if (restartInc > 0_pInt) then
if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0 .and. worldrank == 0_pInt) & if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0 .and. worldrank == 0_pInt) &
write(6,'(/,a,'//IO_intOut(restartInc-1_pInt)//',a)') & write(6,'(/,a,'//IO_intOut(restartInc)//',a)') &
'reading more values of increment', restartInc - 1_pInt, 'from file' 'reading more values of increment ', restartInc, ' from file'
flush(6) flush(6)
call IO_read_realFile(777,'C_volAvg',trim(getSolverJobName()),size(C_volAvg)) call IO_read_realFile(777,'C_volAvg',trim(getSolverJobName()),size(C_volAvg))
read (777,rec=1) C_volAvg read (777,rec=1) C_volAvg; close (777)
close (777)
call IO_read_realFile(777,'C_volAvgLastInc',trim(getSolverJobName()),size(C_volAvgLastInc)) call IO_read_realFile(777,'C_volAvgLastInc',trim(getSolverJobName()),size(C_volAvgLastInc))
read (777,rec=1) C_volAvgLastInc read (777,rec=1) C_volAvgLastInc; close (777)
close (777)
call IO_read_realFile(777,'C_ref',trim(getSolverJobName()),size(C_minMaxAvg)) call IO_read_realFile(777,'C_ref',trim(getSolverJobName()),size(C_minMaxAvg))
read (777,rec=1) C_minMaxAvg read (777,rec=1) C_minMaxAvg; close (777)
close (777)
endif restartRead endif restartRead
call Utilities_updateGamma(C_minMaxAvg,.True.) call Utilities_updateGamma(C_minMaxAvg,.true.)
C_scale = C_minMaxAvg C_scale = C_minMaxAvg
S_scale = math_invSym3333(C_minMaxAvg) S_scale = math_invSym3333(C_minMaxAvg)
@ -245,8 +247,7 @@ end subroutine AL_init
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief solution for the AL scheme with internal iterations !> @brief solution for the AL scheme with internal iterations
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
type(tSolutionState) function & type(tSolutionState) function AL_solution(incInfoIn,timeinc,timeinc_old,stress_BC,rotation_BC)
AL_solution(incInfoIn,timeinc,timeinc_old,stress_BC,rotation_BC)
use IO, only: & use IO, only: &
IO_error IO_error
use numerics, only: & use numerics, only: &
@ -265,13 +266,13 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! input data for solution ! input data for solution
real(pReal), intent(in) :: &
timeinc, & !< increment in time for current solution
timeinc_old !< increment in time of last increment
type(tBoundaryCondition), intent(in) :: &
stress_BC
character(len=*), intent(in) :: & character(len=*), intent(in) :: &
incInfoIn incInfoIn
real(pReal), intent(in) :: &
timeinc, & !< increment time for current solution
timeinc_old !< increment time of last successful increment
type(tBoundaryCondition), intent(in) :: &
stress_BC
real(pReal), dimension(3,3), intent(in) :: rotation_BC real(pReal), dimension(3,3), intent(in) :: rotation_BC
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -304,18 +305,17 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! solve BVP ! solve BVP
call SNESSolve(snes,PETSC_NULL_OBJECT,solution_vec,ierr) call SNESSolve(snes,PETSC_NULL_OBJECT,solution_vec,ierr); CHKERRQ(ierr)
CHKERRQ(ierr)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! check convergence ! check convergence
call SNESGetConvergedReason(snes,reason,ierr) call SNESGetConvergedReason(snes,reason,ierr); CHKERRQ(ierr)
CHKERRQ(ierr)
AL_solution%converged = reason > 0
AL_solution%iterationsNeeded = totalIter
AL_solution%termIll = terminallyIll AL_solution%termIll = terminallyIll
terminallyIll = .false. terminallyIll = .false.
if (reason == -4) call IO_error(893_pInt) if (reason == -4) call IO_error(893_pInt) ! MPI error
if (reason < 1) AL_solution%converged = .false.
AL_solution%iterationsNeeded = totalIter
end function AL_solution end function AL_solution
@ -330,8 +330,8 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
polarAlpha, & polarAlpha, &
polarBeta polarBeta
use mesh, only: & use mesh, only: &
grid3, & grid, &
grid grid3
use IO, only: & use IO, only: &
IO_intOut IO_intOut
use math, only: & use math, only: &
@ -340,6 +340,10 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
math_mul3333xx33, & math_mul3333xx33, &
math_invSym3333, & math_invSym3333, &
math_mul33x33 math_mul33x33
use debug, only: &
debug_level, &
debug_spectral, &
debug_spectralRotation
use spectral_utilities, only: & use spectral_utilities, only: &
wgt, & wgt, &
tensorField_real, & tensorField_real, &
@ -349,27 +353,17 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
Utilities_constitutiveResponse, & Utilities_constitutiveResponse, &
Utilities_divergenceRMS, & Utilities_divergenceRMS, &
Utilities_curlRMS Utilities_curlRMS
use debug, only: &
debug_level, &
debug_spectral, &
debug_spectralRotation
use homogenization, only: & use homogenization, only: &
materialpoint_dPdF materialpoint_dPdF
use FEsolving, only: & use FEsolving, only: &
terminallyIll terminallyIll
implicit none implicit none
!-------------------------------------------------------------------------------------------------- DMDALocalInfo, dimension(DMDA_LOCAL_INFO_SIZE) :: in
! strange syntax in the next line because otherwise macros expand beyond 132 character limit PetscScalar, &
DMDALocalInfo, dimension(& target, dimension(3,3,2, XG_RANGE,YG_RANGE,ZG_RANGE), intent(in) :: x_scal !< what is this?
DMDA_LOCAL_INFO_SIZE) :: & PetscScalar, &
in target, dimension(3,3,2, X_RANGE,Y_RANGE,Z_RANGE), intent(out) :: f_scal !< what is this?
PetscScalar, target, dimension(3,3,2, &
XG_RANGE,YG_RANGE,ZG_RANGE), intent(in) :: &
x_scal
PetscScalar, target, dimension(3,3,2, &
X_RANGE,Y_RANGE,Z_RANGE), intent(out) :: &
f_scal
PetscScalar, pointer, dimension(:,:,:,:,:) :: & PetscScalar, pointer, dimension(:,:,:,:,:) :: &
F, & F, &
F_lambda, & F_lambda, &
@ -392,28 +386,28 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
F_lambda => x_scal(1:3,1:3,2,& F_lambda => x_scal(1:3,1:3,2,&
XG_RANGE,YG_RANGE,ZG_RANGE) XG_RANGE,YG_RANGE,ZG_RANGE)
residual_F => f_scal(1:3,1:3,1,& residual_F => f_scal(1:3,1:3,1,&
X_RANGE,Y_RANGE,Z_RANGE) X_RANGE, Y_RANGE, Z_RANGE)
residual_F_lambda => f_scal(1:3,1:3,2,& residual_F_lambda => f_scal(1:3,1:3,2,&
X_RANGE,Y_RANGE,Z_RANGE) X_RANGE, Y_RANGE, Z_RANGE)
call SNESGetNumberFunctionEvals(snes,nfuncs,ierr); CHKERRQ(ierr)
call SNESGetIterationNumber(snes,PETScIter,ierr); CHKERRQ(ierr)
F_av = sum(sum(sum(F,dim=5),dim=4),dim=3) * wgt F_av = sum(sum(sum(F,dim=5),dim=4),dim=3) * wgt
call MPI_Allreduce(MPI_IN_PLACE,F_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,F_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
if(nfuncs== 0 .and. PETScIter == 0) totalIter = -1_pInt ! new increment call SNESGetNumberFunctionEvals(snes,nfuncs,ierr); CHKERRQ(ierr)
newIteration: if(totalIter <= PETScIter) then call SNESGetIterationNumber(snes,PETScIter,ierr); CHKERRQ(ierr)
if (nfuncs == 0 .and. PETScIter == 0) totalIter = -1_pInt ! new increment
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report begin of new iteration ! begin of new iteration
newIteration: if (totalIter <= PETScIter) then
totalIter = totalIter + 1_pInt totalIter = totalIter + 1_pInt
write(6,'(1x,a,3(a,'//IO_intOut(itmax)//'))') trim(incInfo), & write(6,'(1x,a,3(a,'//IO_intOut(itmax)//'))') &
' @ Iteration ', itmin, '≤',totalIter, '≤', itmax trim(incInfo), ' @ Iteration ', itmin, '≤',totalIter, '≤', itmax
if (iand(debug_level(debug_spectral),debug_spectralRotation) /= 0) & if (iand(debug_level(debug_spectral),debug_spectralRotation) /= 0) &
write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') ' deformation gradient aim (lab) =', & write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') &
math_transpose33(math_rotate_backward33(F_aim,params%rotation_BC)) ' deformation gradient aim (lab) =', math_transpose33(math_rotate_backward33(F_aim,params%rotation_BC))
write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') ' deformation gradient aim =', & write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') &
math_transpose33(F_aim) ' deformation gradient aim =', math_transpose33(F_aim)
flush(6) flush(6)
endif newIteration endif newIteration
@ -425,7 +419,6 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
polarBeta*math_mul3333xx33(C_scale,F(1:3,1:3,i,j,k) - math_I3) -& polarBeta*math_mul3333xx33(C_scale,F(1:3,1:3,i,j,k) - math_I3) -&
polarAlpha*math_mul33x33(F(1:3,1:3,i,j,k), & polarAlpha*math_mul33x33(F(1:3,1:3,i,j,k), &
math_mul3333xx33(C_scale,F_lambda(1:3,1:3,i,j,k) - math_I3)) math_mul3333xx33(C_scale,F_lambda(1:3,1:3,i,j,k) - math_I3))
enddo; enddo; enddo enddo; enddo; enddo
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -435,24 +428,23 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
call utilities_FFTtensorBackward() call utilities_FFTtensorBackward()
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! constructing residual ! constructing F_lambda residual
residual_F_lambda = polarBeta*F - tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) residual_F_lambda = polarBeta*F - tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) !< eq (16) in doi: 10.1016/j.ijplas.2014.02.006
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! evaluate constitutive response ! evaluate constitutive response
P_avLastEval = P_av P_avLastEval = P_av
call Utilities_constitutiveResponse(F_lastInc,F - residual_F_lambda/polarBeta,params%timeinc, &
residual_F,C_volAvg,C_minMaxAvg,P_av,ForwardData,params%rotation_BC) call Utilities_constitutiveResponse(residual_F,P_av,C_volAvg,C_minMaxAvg, &
F - residual_F_lambda/polarBeta,params%timeinc, params%rotation_BC)
call MPI_Allreduce(MPI_IN_PLACE,terminallyIll,1,MPI_LOGICAL,MPI_LOR,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,terminallyIll,1,MPI_LOGICAL,MPI_LOR,PETSC_COMM_WORLD,ierr)
ForwardData = .False.
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! calculate divergence ! calculate divergence
tensorField_real = 0.0_pReal tensorField_real = 0.0_pReal
tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = residual_F tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = residual_F !< stress field in disguise
call utilities_FFTtensorForward() call utilities_FFTtensorForward()
err_div = Utilities_divergenceRMS() err_div = Utilities_divergenceRMS() !< root mean squared error in divergence of stress
call utilities_FFTtensorBackward()
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! constructing residual ! constructing residual
@ -463,7 +455,7 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
residual_F(1:3,1:3,i,j,k) - & residual_F(1:3,1:3,i,j,k) - &
math_mul33x33(F(1:3,1:3,i,j,k), & math_mul33x33(F(1:3,1:3,i,j,k), &
math_mul3333xx33(C_scale,F_lambda(1:3,1:3,i,j,k) - math_I3))) & math_mul3333xx33(C_scale,F_lambda(1:3,1:3,i,j,k) - math_I3))) &
+ residual_F_lambda(1:3,1:3,i,j,k) + residual_F_lambda(1:3,1:3,i,j,k) !< eq (16) in doi: 10.1016/j.ijplas.2014.02.006
enddo; enddo; enddo enddo; enddo; enddo
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -472,8 +464,11 @@ subroutine AL_formResidual(in,x_scal,f_scal,dummy,ierr)
tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = F tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = F
call utilities_FFTtensorForward() call utilities_FFTtensorForward()
err_curl = Utilities_curlRMS() err_curl = Utilities_curlRMS()
call utilities_FFTtensorBackward()
nullify(F)
nullify(F_lambda)
nullify(residual_F)
nullify(residual_F_lambda)
end subroutine AL_formResidual end subroutine AL_formResidual
@ -488,8 +483,8 @@ subroutine AL_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,dummy,ierr
err_div_tolAbs, & err_div_tolAbs, &
err_curl_tolRel, & err_curl_tolRel, &
err_curl_tolAbs, & err_curl_tolAbs, &
err_stress_tolAbs, & err_stress_tolRel, &
err_stress_tolRel err_stress_tolAbs
use math, only: & use math, only: &
math_mul3333xx33 math_mul3333xx33
use FEsolving, only: & use FEsolving, only: &
@ -508,24 +503,24 @@ subroutine AL_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,dummy,ierr
real(pReal) :: & real(pReal) :: &
curlTol, & curlTol, &
divTol, & divTol, &
BC_tol BCTol
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! stress BC handling ! stress BC handling
F_aim = F_aim - math_mul3333xx33(S, ((P_av - params%stress_BC))) ! S = 0.0 for no bc F_aim = F_aim - math_mul3333xx33(S, ((P_av - params%stress_BC))) ! S = 0.0 for no bc
err_BC = maxval(abs((-mask_stress+1.0_pReal)*math_mul3333xx33(C_scale,F_aim-F_av) + & err_BC = maxval(abs((1.0_pReal-mask_stress) * math_mul3333xx33(C_scale,F_aim-F_av) + &
mask_stress *(P_av - params%stress_BC))) ! mask = 0.0 for no bc mask_stress * (P_av-params%stress_BC))) ! mask = 0.0 for no bc
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! error calculation ! error calculation
curlTol = max(maxval(abs(F_aim-math_I3))*err_curl_tolRel,err_curl_tolAbs) curlTol = max(maxval(abs(F_aim-math_I3))*err_curl_tolRel ,err_curl_tolAbs)
divTol = max(maxval(abs(P_av)) *err_div_tolRel,err_div_tolAbs) divTol = max(maxval(abs(P_av)) *err_div_tolRel ,err_div_tolAbs)
BC_tol = max(maxval(abs(P_av)) *err_stress_tolrel,err_stress_tolabs) BCTol = max(maxval(abs(P_av)) *err_stress_tolRel,err_stress_tolAbs)
converged: if ((totalIter >= itmin .and. & converged: if ((totalIter >= itmin .and. &
all([ err_div/divTol, & all([ err_div /divTol, &
err_curl/curlTol, & err_curl/curlTol, &
err_BC/BC_tol ] < 1.0_pReal)) & err_BC /BCTol ] < 1.0_pReal)) &
.or. terminallyIll) then .or. terminallyIll) then
reason = 1 reason = 1
elseif (totalIter >= itmax) then converged elseif (totalIter >= itmax) then converged
@ -537,12 +532,12 @@ subroutine AL_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,dummy,ierr
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report ! report
write(6,'(1/,a)') ' ... reporting .............................................................' write(6,'(1/,a)') ' ... reporting .............................................................'
write(6,'(/,a,f12.2,a,es8.2,a,es9.2,a)') ' error curl = ', & write(6,'(/,a,f12.2,a,es8.2,a,es9.2,a)') ' error divergence = ', &
err_curl/curlTol,' (',err_curl,' -, tol =',curlTol,')' err_div/divTol, ' (',err_div, ' / m, tol = ',divTol,')'
write(6,' (a,f12.2,a,es8.2,a,es9.2,a)') ' error divergence = ', & write(6, '(a,f12.2,a,es8.2,a,es9.2,a)') ' error curl = ', &
err_div/divTol, ' (',err_div, ' / m, tol =',divTol,')' err_curl/curlTol,' (',err_curl,' -, tol = ',curlTol,')'
write(6,' (a,f12.2,a,es8.2,a,es9.2,a)') ' error BC = ', & write(6, '(a,f12.2,a,es8.2,a,es9.2,a)') ' error BC = ', &
err_BC/BC_tol, ' (',err_BC, ' Pa, tol =',BC_tol,')' err_BC/BCTol, ' (',err_BC, ' Pa, tol = ',BCTol,')'
write(6,'(/,a)') ' ===========================================================================' write(6,'(/,a)') ' ==========================================================================='
flush(6) flush(6)
@ -550,6 +545,8 @@ end subroutine AL_converged
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief forwarding routine !> @brief forwarding routine
!> @details find new boundary conditions and best F estimate for end of current timestep
!> possibly writing restart information, triggering of state increment in DAMASK, and updating of IPcoordinates
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine AL_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stress_BC,rotation_BC) subroutine AL_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stress_BC,rotation_BC)
use math, only: & use math, only: &
@ -559,9 +556,13 @@ subroutine AL_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stre
math_rotate_backward33 math_rotate_backward33
use numerics, only: & use numerics, only: &
worldrank worldrank
use homogenization, only: &
materialpoint_F0
use mesh, only: & use mesh, only: &
grid3, & grid, &
grid grid3
use CPFEM2, only: &
CPFEM_age
use spectral_utilities, only: & use spectral_utilities, only: &
Utilities_calculateRate, & Utilities_calculateRate, &
Utilities_forwardField, & Utilities_forwardField, &
@ -574,6 +575,8 @@ subroutine AL_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stre
restartWrite restartWrite
implicit none implicit none
logical, intent(in) :: &
guess
real(pReal), intent(in) :: & real(pReal), intent(in) :: &
timeinc_old, & timeinc_old, &
timeinc, & timeinc, &
@ -581,98 +584,102 @@ subroutine AL_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stre
type(tBoundaryCondition), intent(in) :: & type(tBoundaryCondition), intent(in) :: &
stress_BC, & stress_BC, &
deformation_BC deformation_BC
real(pReal), dimension(3,3), intent(in) :: rotation_BC real(pReal), dimension(3,3), intent(in) ::&
logical, intent(in) :: & rotation_BC
guess
PetscErrorCode :: ierr PetscErrorCode :: ierr
PetscScalar, dimension(:,:,:,:), pointer :: xx_psc, F, F_lambda PetscScalar, dimension(:,:,:,:), pointer :: FandF_lambda, F, F_lambda
integer(pInt) :: i, j, k integer(pInt) :: i, j, k
real(pReal), dimension(3,3) :: F_lambda33 real(pReal), dimension(3,3) :: F_lambda33
character(len=1024) :: rankStr character(len=32) :: rankStr
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! update coordinates and rate and forward last inc ! update coordinates and rate and forward last inc
call DMDAVecGetArrayF90(da,solution_vec,xx_psc,ierr) call DMDAVecGetArrayF90(da,solution_vec,FandF_lambda,ierr); CHKERRQ(ierr)
F => xx_psc(0:8,:,:,:) F => FandF_lambda( 0: 8,:,:,:)
F_lambda => xx_psc(9:17,:,:,:) F_lambda => FandF_lambda( 9:17,:,:,:)
if (restartWrite) then
write(6,'(/,a)') ' writing converged results for restart'
flush(6)
write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'F'//trim(rankStr),size(F)) ! writing deformation gradient field to file
write (777,rec=1) F
close (777)
call IO_write_jobRealFile(777,'F_lastInc'//trim(rankStr),size(F_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lastInc
close (777)
call IO_write_jobRealFile(777,'F_lambda'//trim(rankStr),size(F_lambda)) ! writing deformation gradient field to file
write (777,rec=1) F_lambda
close (777)
call IO_write_jobRealFile(777,'F_lambda_lastInc'//trim(rankStr),size(F_lambda_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lambda_lastInc
close (777)
if (worldrank == 0_pInt) then
call IO_write_jobRealFile(777,'F_aim',size(F_aim))
write (777,rec=1) F_aim
close(777)
call IO_write_jobRealFile(777,'F_aim_lastInc',size(F_aim_lastInc))
write (777,rec=1) F_aim_lastInc
close(777)
call IO_write_jobRealFile(777,'F_aimDot',size(F_aimDot))
write (777,rec=1) F_aimDot
close(777)
call IO_write_jobRealFile(777,'C_volAvg',size(C_volAvg))
write (777,rec=1) C_volAvg
close(777)
call IO_write_jobRealFile(777,'C_volAvgLastInc',size(C_volAvgLastInc))
write (777,rec=1) C_volAvgLastInc
close(777)
endif
endif
call utilities_updateIPcoords(F)
if (cutBack) then if (cutBack) then
F_aim = F_aim_lastInc C_volAvg = C_volAvgLastInc ! QUESTION: where is this required?
F_lambda = reshape(F_lambda_lastInc,[9,grid(1),grid(2),grid3]) C_minMaxAvg = C_minMaxAvgLastInc ! QUESTION: where is this required?
F = reshape(F_lastInc, [9,grid(1),grid(2),grid3])
C_volAvg = C_volAvgLastInc
else else
ForwardData = .True. !--------------------------------------------------------------------------------------------------
C_volAvgLastInc = C_volAvg ! restart information for spectral solver
!-------------------------------------------------------------------------------------------------- if (restartWrite) then ! QUESTION: where is this logical properly set?
! calculate rate for aim write(6,'(/,a)') ' writing converged results for restart'
if (deformation_BC%myType=='l') then ! calculate f_aimDot from given L and current F flush(6)
f_aimDot = deformation_BC%maskFloat * math_mul33x33(deformation_BC%values, F_aim)
elseif(deformation_BC%myType=='fdot') then ! f_aimDot is prescribed
f_aimDot = deformation_BC%maskFloat * deformation_BC%values
elseif(deformation_BC%myType=='f') then ! aim at end of load case is prescribed
f_aimDot = deformation_BC%maskFloat * (deformation_BC%values -F_aim)/loadCaseTime
endif
if (guess) f_aimDot = f_aimDot + stress_BC%maskFloat * (F_aim - F_aim_lastInc)/timeinc_old
F_aim_lastInc = F_aim
!-------------------------------------------------------------------------------------------------- if (worldrank == 0_pInt) then
! update coordinates and rate and forward last inc call IO_write_jobRealFile(777,'C_volAvg',size(C_volAvg))
write (777,rec=1) C_volAvg; close(777)
call IO_write_jobRealFile(777,'C_volAvgLastInc',size(C_volAvgLastInc))
write (777,rec=1) C_volAvgLastInc; close(777)
! call IO_write_jobRealFile(777,'C_minMaxAvg',size(C_volAvg))
! write (777,rec=1) C_minMaxAvg; close(777)
! call IO_write_jobRealFile(777,'C_minMaxAvgLastInc',size(C_volAvgLastInc))
! write (777,rec=1) C_minMaxAvgLastInc; close(777)
call IO_write_jobRealFile(777,'F_aimDot',size(F_aimDot))
write (777,rec=1) F_aimDot; close(777)
endif
write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'F'//trim(rankStr),size(F)) ! writing deformation gradient field to file
write (777,rec=1) F; close (777)
call IO_write_jobRealFile(777,'F_lastInc'//trim(rankStr),size(F_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lastInc; close (777)
call IO_write_jobRealFile(777,'F_lambda'//trim(rankStr),size(F_lambda)) ! writing deformation gradient field to file
write (777,rec=1) F_lambda; close (777)
call IO_write_jobRealFile(777,'F_lambda_lastInc'//trim(rankStr),size(F_lambda_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lambda_lastInc; close (777)
endif
call CPFEM_age() ! age state and kinematics
call utilities_updateIPcoords(F) call utilities_updateIPcoords(F)
Fdot = Utilities_calculateRate(math_rotate_backward33(f_aimDot,rotation_BC), &
timeinc_old,guess,F_lastInc,reshape(F,[3,3,grid(1),grid(2),grid3])) C_volAvgLastInc = C_volAvg
F_lambdaDot = Utilities_calculateRate(math_rotate_backward33(f_aimDot,rotation_BC), & C_minMaxAvgLastInc = C_minMaxAvg
timeinc_old,guess,F_lambda_lastInc,reshape(F_lambda,[3,3,grid(1),grid(2),grid3]))
F_lastInc = reshape(F, [3,3,grid(1),grid(2),grid3]) if (guess) then ! QUESTION: better with a = L ? x:y
F_lambda_lastInc = reshape(F_lambda,[3,3,grid(1),grid(2),grid3]) F_aimDot = stress_BC%maskFloat * (F_aim - F_aim_lastInc)/timeinc_old ! initialize with correction based on last inc
else
F_aimDot = 0.0_pReal
endif
F_aim_lastInc = F_aim
!--------------------------------------------------------------------------------------------------
! calculate rate for aim
if (deformation_BC%myType=='l') then ! calculate F_aimDot from given L and current F
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * math_mul33x33(deformation_BC%values, F_aim_lastInc)
elseif(deformation_BC%myType=='fdot') then ! F_aimDot is prescribed
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * deformation_BC%values
elseif (deformation_BC%myType=='f') then ! aim at end of load case is prescribed
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * (deformation_BC%values - F_aim_lastInc)/loadCaseTime
endif endif
F_aim = F_aim + f_aimDot * timeinc
Fdot = Utilities_calculateRate(guess, &
F_lastInc,reshape(F,[3,3,grid(1),grid(2),grid3]),timeinc_old, &
math_rotate_backward33(F_aimDot,rotation_BC))
F_lambdaDot = Utilities_calculateRate(guess, &
F_lambda_lastInc,reshape(F_lambda,[3,3,grid(1),grid(2),grid3]), timeinc_old, &
math_rotate_backward33(F_aimDot,rotation_BC))
F_lastInc = reshape(F, [3,3,grid(1),grid(2),grid3]) ! winding F forward
F_lambda_lastInc = reshape(F_lambda, [3,3,grid(1),grid(2),grid3]) ! winding F_lambda forward
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3]) ! set starting condition for materialpoint_stressAndItsTangent
endif
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! update local deformation gradient ! update average and local deformation gradients
F = reshape(Utilities_forwardField(timeinc,F_lastInc,Fdot, & ! ensure that it matches rotated F_aim F_aim = F_aim_lastInc + F_aimDot * timeinc
math_rotate_backward33(F_aim,rotation_BC)), &
F = reshape(Utilities_forwardField(timeinc,F_lastInc,Fdot, & ! estimate of F at end of time+timeinc that matches rotated F_aim on average
math_rotate_backward33(F_aim,rotation_BC)),&
[9,grid(1),grid(2),grid3]) [9,grid(1),grid(2),grid3])
if (guess) then
F_lambda = reshape(Utilities_forwardField(timeinc,F_lambda_lastInc,F_lambdadot), & F_lambda = reshape(Utilities_forwardField(timeinc,F_lambda_lastInc,F_lambdadot), &
[9,grid(1),grid(2),grid3]) ! does not have any average value as boundary condition [9,grid(1),grid(2),grid3]) ! does not have any average value as boundary condition
if (.not. guess) then ! large strain forwarding else
do k = 1_pInt, grid3; do j = 1_pInt, grid(2); do i = 1_pInt, grid(1) do k = 1_pInt, grid3; do j = 1_pInt, grid(2); do i = 1_pInt, grid(1)
F_lambda33 = reshape(F_lambda(1:9,i,j,k),[3,3]) F_lambda33 = reshape(F_lambda(1:9,i,j,k),[3,3])
F_lambda33 = math_mul3333xx33(S_scale,math_mul33x33(F_lambda33, & F_lambda33 = math_mul3333xx33(S_scale,math_mul33x33(F_lambda33, &
@ -683,7 +690,10 @@ subroutine AL_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stre
F_lambda(1:9,i,j,k) = reshape(F_lambda33,[9]) F_lambda(1:9,i,j,k) = reshape(F_lambda33,[9])
enddo; enddo; enddo enddo; enddo; enddo
endif endif
call DMDAVecRestoreArrayF90(da,solution_vec,xx_psc,ierr); CHKERRQ(ierr)
nullify(F)
nullify(F_lambda)
call DMDAVecRestoreArrayF90(da,solution_vec,FandF_lambda,ierr); CHKERRQ(ierr)
end subroutine AL_forward end subroutine AL_forward

View File

@ -38,21 +38,27 @@ module spectral_mech_basic
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! stress, stiffness and compliance average etc. ! stress, stiffness and compliance average etc.
real(pReal), private, dimension(3,3) :: & real(pReal), private, dimension(3,3) :: &
F_aim = math_I3, & F_aimDot = 0.0_pReal, & !< assumed rate of average deformation gradient
F_aim_lastIter = math_I3, & F_aim = math_I3, & !< current prescribed deformation gradient
F_aim_lastInc = math_I3, & F_aim_lastInc = math_I3, & !< previous average deformation gradient
P_av = 0.0_pReal, & P_av = 0.0_pReal !< average 1st Piola--Kirchhoff stress
F_aimDot=0.0_pReal
character(len=1024), private :: incInfo character(len=1024), private :: incInfo !< time and increment information
real(pReal), private, dimension(3,3,3,3) :: & real(pReal), private, dimension(3,3,3,3) :: &
C_volAvg = 0.0_pReal, & !< current volume average stiffness C_volAvg = 0.0_pReal, & !< current volume average stiffness
C_volAvgLastInc = 0.0_pReal, & !< previous volume average stiffness C_volAvgLastInc = 0.0_pReal, & !< previous volume average stiffness
C_minMaxAvg = 0.0_pReal, & !< current (min+max)/2 stiffness C_minMaxAvg = 0.0_pReal, & !< current (min+max)/2 stiffness
C_minMaxAvgLastInc = 0.0_pReal, & !< previous (min+max)/2 stiffness
S = 0.0_pReal !< current compliance (filled up with zeros) S = 0.0_pReal !< current compliance (filled up with zeros)
real(pReal), private :: err_stress, err_div
logical, private :: ForwardData real(pReal), private :: &
err_BC, & !< deviation from stress BC
err_div !< RMS of div of P
integer(pInt), private :: & integer(pInt), private :: &
totalIter = 0_pInt !< total iteration in current increment totalIter = 0_pInt !< total iteration in current increment
real(pReal), private, dimension(3,3) :: mask_stress = 0.0_pReal real(pReal), private, dimension(3,3) :: mask_stress = 0.0_pReal
public :: & public :: &
@ -69,7 +75,7 @@ module spectral_mech_basic
contains contains
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief allocates all neccessary fields and fills them with data, potentially from restart info !> @brief allocates all necessary fields and fills them with data, potentially from restart info
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine basicPETSc_init subroutine basicPETSc_init
#if defined(__GFORTRAN__) || __INTEL_COMPILER >= 1800 #if defined(__GFORTRAN__) || __INTEL_COMPILER >= 1800
@ -90,6 +96,8 @@ subroutine basicPETSc_init
use numerics, only: & use numerics, only: &
worldrank, & worldrank, &
worldsize worldsize
use homogenization, only: &
materialpoint_F0
use DAMASK_interface, only: & use DAMASK_interface, only: &
getSolverJobName getSolverJobName
use spectral_utilities, only: & use spectral_utilities, only: &
@ -152,11 +160,10 @@ subroutine basicPETSc_init
grid(1),grid(2),localK, & ! local grid grid(1),grid(2),localK, & ! local grid
da,ierr) ! handle, error da,ierr) ! handle, error
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) ! connect snes to da
call DMCreateGlobalVector(da,solution_vec,ierr); CHKERRQ(ierr) ! global solution vector (grid x 9, i.e. every def grad tensor) call DMCreateGlobalVector(da,solution_vec,ierr); CHKERRQ(ierr) ! global solution vector (grid x 9, i.e. every def grad tensor)
call DMDASNESSetFunctionLocal(da,INSERT_VALUES,BasicPETSC_formResidual,PETSC_NULL_OBJECT,ierr) ! residual vector of same shape as solution vector call DMDASNESSetFunctionLocal(da,INSERT_VALUES,BasicPETSC_formResidual,PETSC_NULL_OBJECT,ierr) ! residual vector of same shape as solution vector
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) ! connect snes to da
call SNESSetConvergenceTest(snes,BasicPETSC_converged,PETSC_NULL_OBJECT,PETSC_NULL_FUNCTION,ierr) ! specify custom convergence check function "_converged" call SNESSetConvergenceTest(snes,BasicPETSC_converged,PETSC_NULL_OBJECT,PETSC_NULL_FUNCTION,ierr) ! specify custom convergence check function "_converged"
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetFromOptions(snes,ierr); CHKERRQ(ierr) ! pull it all together with additional cli arguments call SNESSetFromOptions(snes,ierr); CHKERRQ(ierr) ! pull it all together with additional cli arguments
@ -165,63 +172,56 @@ subroutine basicPETSc_init
! init fields ! init fields
call DMDAVecGetArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr) ! get the data out of PETSc to work with call DMDAVecGetArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr) ! get the data out of PETSc to work with
restart: if (restartInc > 1_pInt) then restart: if (restartInc > 0_pInt) then
if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0) & if (iand(debug_level(debug_spectral),debug_spectralRestart) /= 0) then
write(6,'(/,a,'//IO_intOut(restartInc-1_pInt)//',a)') & write(6,'(/,a,'//IO_intOut(restartInc)//',a)') &
'reading values of increment ', restartInc - 1_pInt, ' from file' 'reading values of increment ', restartInc, ' from file'
flush(6) flush(6)
endif
write(rankStr,'(a1,i0)')'_',worldrank write(rankStr,'(a1,i0)')'_',worldrank
call IO_read_realFile(777,'F'//trim(rankStr),trim(getSolverJobName()),size(F)) call IO_read_realFile(777,'F'//trim(rankStr),trim(getSolverJobName()),size(F))
read (777,rec=1) F read (777,rec=1) F; close (777)
close (777)
call IO_read_realFile(777,'F_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lastInc)) call IO_read_realFile(777,'F_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lastInc))
read (777,rec=1) F_lastInc read (777,rec=1) F_lastInc; close (777)
close (777) call IO_read_realFile(777,'F_aimDot',trim(getSolverJobName()),size(F_aimDot))
call IO_read_realFile(777,'F_aimDot',trim(getSolverJobName()),size(f_aimDot)) read (777,rec=1) F_aimDot; close (777)
read (777,rec=1) f_aimDot
close (777)
F_aim = reshape(sum(sum(sum(F,dim=4),dim=3),dim=2) * wgt, [3,3]) ! average of F F_aim = reshape(sum(sum(sum(F,dim=4),dim=3),dim=2) * wgt, [3,3]) ! average of F
F_aim_lastInc = sum(sum(sum(F_lastInc,dim=5),dim=4),dim=3) * wgt ! average of F_lastInc F_aim_lastInc = sum(sum(sum(F_lastInc,dim=5),dim=4),dim=3) * wgt ! average of F_lastInc
elseif (restartInc == 1_pInt) then restart elseif (restartInc == 0_pInt) then restart
F_lastInc = spread(spread(spread(math_I3,3,grid(1)),4,grid(2)),5,grid3) ! initialize to identity F_lastInc = spread(spread(spread(math_I3,3,grid(1)),4,grid(2)),5,grid3) ! initialize to identity
F = reshape(F_lastInc,[9,grid(1),grid(2),grid3]) F = reshape(F_lastInc,[9,grid(1),grid(2),grid3])
endif restart endif restart
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3]) ! set starting condition for materialpoint_stressAndItsTangent
call Utilities_updateIPcoords(reshape(F,shape(F_lastInc))) call Utilities_updateIPcoords(reshape(F,shape(F_lastInc)))
call Utilities_constitutiveResponse(F_lastInc, reshape(F,shape(F_lastInc)), & call Utilities_constitutiveResponse(P,temp33_Real,C_volAvg,C_minMaxAvg, & ! stress field, stress avg, global average of stiffness and (min+max)/2
0.0_pReal, & reshape(F,shape(F_lastInc)), & ! target F
P, & 0.0_pReal, & ! time increment
C_volAvg,C_minMaxAvg, & ! global average of stiffness and (min+max)/2 math_I3) ! no rotation of boundary condition
temp33_Real, &
.false., &
math_I3)
call DMDAVecRestoreArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr) ! write data back to PETSc call DMDAVecRestoreArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr) ! write data back to PETSc
! QUESTION: why not writing back right after reading (l.189)?
restartRead: if (restartInc > 1_pInt) then restartRead: if (restartInc > 0_pInt) then ! QUESTION: are those values not calc'ed by constitutiveResponse? why reading from file?
if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0 .and. worldrank == 0_pInt) & if (iand(debug_level(debug_spectral),debug_spectralRestart) /= 0 .and. worldrank == 0_pInt) &
write(6,'(/,a,'//IO_intOut(restartInc-1_pInt)//',a)') & write(6,'(/,a,'//IO_intOut(restartInc)//',a)') &
'reading more values of increment', restartInc - 1_pInt, 'from file' 'reading more values of increment ', restartInc, ' from file'
flush(6) flush(6)
call IO_read_realFile(777,'C_volAvg',trim(getSolverJobName()),size(C_volAvg)) call IO_read_realFile(777,'C_volAvg',trim(getSolverJobName()),size(C_volAvg))
read (777,rec=1) C_volAvg read (777,rec=1) C_volAvg; close (777)
close (777)
call IO_read_realFile(777,'C_volAvgLastInc',trim(getSolverJobName()),size(C_volAvgLastInc)) call IO_read_realFile(777,'C_volAvgLastInc',trim(getSolverJobName()),size(C_volAvgLastInc))
read (777,rec=1) C_volAvgLastInc read (777,rec=1) C_volAvgLastInc; close (777)
close (777)
call IO_read_realFile(777,'C_ref',trim(getSolverJobName()),size(C_minMaxAvg)) call IO_read_realFile(777,'C_ref',trim(getSolverJobName()),size(C_minMaxAvg))
read (777,rec=1) C_minMaxAvg read (777,rec=1) C_minMaxAvg; close (777)
close (777)
endif restartRead endif restartRead
call Utilities_updateGamma(C_minmaxAvg,.True.) call Utilities_updateGamma(C_minMaxAvg,.true.)
end subroutine basicPETSc_init end subroutine basicPETSc_init
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief solution for the Basic PETSC scheme with internal iterations !> @brief solution for the Basic PETSC scheme with internal iterations
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
type(tSolutionState) function & type(tSolutionState) function basicPETSc_solution(incInfoIn,timeinc,timeinc_old,stress_BC,rotation_BC)
basicPETSc_solution(incInfoIn,timeinc,timeinc_old,stress_BC,rotation_BC)
use IO, only: & use IO, only: &
IO_error IO_error
use numerics, only: & use numerics, only: &
@ -238,13 +238,13 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! input data for solution ! input data for solution
real(pReal), intent(in) :: &
timeinc, & !< increment in time for current solution
timeinc_old !< increment in time of last increment
type(tBoundaryCondition), intent(in) :: &
stress_BC
character(len=*), intent(in) :: & character(len=*), intent(in) :: &
incInfoIn incInfoIn
real(pReal), intent(in) :: &
timeinc, & !< increment time for current solution
timeinc_old !< increment time of last successful increment
type(tBoundaryCondition), intent(in) :: &
stress_BC
real(pReal), dimension(3,3), intent(in) :: rotation_BC real(pReal), dimension(3,3), intent(in) :: rotation_BC
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -261,7 +261,7 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! update stiffness (and gamma operator) ! update stiffness (and gamma operator)
S = Utilities_maskedCompliance(rotation_BC,stress_BC%maskLogical,C_volAvg) S = Utilities_maskedCompliance(rotation_BC,stress_BC%maskLogical,C_volAvg)
if (update_gamma) call Utilities_updateGamma(C_minmaxAvg,restartWrite) if (update_gamma) call Utilities_updateGamma(C_minMaxAvg,restartWrite)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -274,19 +274,17 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! solve BVP ! solve BVP
call SNESSolve(snes,PETSC_NULL_OBJECT,solution_vec,ierr) call SNESSolve(snes,PETSC_NULL_OBJECT,solution_vec,ierr); CHKERRQ(ierr)
CHKERRQ(ierr)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! check convergence ! check convergence
call SNESGetConvergedReason(snes,reason,ierr) call SNESGetConvergedReason(snes,reason,ierr); CHKERRQ(ierr)
CHKERRQ(ierr)
BasicPETSc_solution%converged = reason > 0
basicPETSC_solution%iterationsNeeded = totalIter
basicPETSc_solution%termIll = terminallyIll basicPETSc_solution%termIll = terminallyIll
terminallyIll = .false. terminallyIll = .false.
BasicPETSc_solution%converged =.true. if (reason == -4) call IO_error(893_pInt) ! MPI error
if (reason == -4) call IO_error(893_pInt)
if (reason < 1) basicPETSC_solution%converged = .false.
basicPETSC_solution%iterationsNeeded = totalIter
end function BasicPETSc_solution end function BasicPETSc_solution
@ -322,19 +320,18 @@ subroutine BasicPETSC_formResidual(in,x_scal,f_scal,dummy,ierr)
terminallyIll terminallyIll
implicit none implicit none
DMDALocalInfo, dimension(DMDA_LOCAL_INFO_SIZE) :: & DMDALocalInfo, dimension(DMDA_LOCAL_INFO_SIZE) :: in
in PetscScalar, &
PetscScalar, dimension(3,3, & dimension(3,3, XG_RANGE,YG_RANGE,ZG_RANGE), intent(in) :: x_scal !< what is this?
XG_RANGE,YG_RANGE,ZG_RANGE), intent(in) :: & PetscScalar, &
x_scal dimension(3,3, X_RANGE,Y_RANGE,Z_RANGE), intent(out) :: f_scal !< what is this?
PetscScalar, dimension(3,3, &
X_RANGE,Y_RANGE,Z_RANGE), intent(out) :: &
f_scal
PetscInt :: & PetscInt :: &
PETScIter, & PETScIter, &
nfuncs nfuncs
PetscObject :: dummy PetscObject :: dummy
PetscErrorCode :: ierr PetscErrorCode :: ierr
real(pReal), dimension(3,3) :: &
deltaF_aim
external :: & external :: &
SNESGetNumberFunctionEvals, & SNESGetNumberFunctionEvals, &
@ -343,46 +340,45 @@ subroutine BasicPETSC_formResidual(in,x_scal,f_scal,dummy,ierr)
call SNESGetNumberFunctionEvals(snes,nfuncs,ierr); CHKERRQ(ierr) call SNESGetNumberFunctionEvals(snes,nfuncs,ierr); CHKERRQ(ierr)
call SNESGetIterationNumber(snes,PETScIter,ierr); CHKERRQ(ierr) call SNESGetIterationNumber(snes,PETScIter,ierr); CHKERRQ(ierr)
if(nfuncs== 0 .and. PETScIter == 0) totalIter = -1_pInt ! new increment if (nfuncs == 0 .and. PETScIter == 0) totalIter = -1_pInt ! new increment
newIteration: if(totalIter <= PETScIter) then
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report begin of new iteration ! begin of new iteration
newIteration: if (totalIter <= PETScIter) then
totalIter = totalIter + 1_pInt totalIter = totalIter + 1_pInt
write(6,'(1x,a,3(a,'//IO_intOut(itmax)//'))') trim(incInfo), & write(6,'(1x,a,3(a,'//IO_intOut(itmax)//'))') &
' @ Iteration ', itmin, '≤',totalIter, '≤', itmax trim(incInfo), ' @ Iteration ', itmin, '≤',totalIter, '≤', itmax
if (iand(debug_level(debug_spectral),debug_spectralRotation) /= 0) & if (iand(debug_level(debug_spectral),debug_spectralRotation) /= 0) &
write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') ' deformation gradient aim (lab) =', & write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') &
math_transpose33(math_rotate_backward33(F_aim,params%rotation_BC)) ' deformation gradient aim (lab) =', math_transpose33(math_rotate_backward33(F_aim,params%rotation_BC))
write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') ' deformation gradient aim =', & write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') &
math_transpose33(F_aim) ' deformation gradient aim =', math_transpose33(F_aim)
flush(6) flush(6)
endif newIteration endif newIteration
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! evaluate constitutive response ! evaluate constitutive response
call Utilities_constitutiveResponse(F_lastInc,x_scal,params%timeinc, & call Utilities_constitutiveResponse(f_scal,P_av,C_volAvg,C_minMaxAvg, &
f_scal,C_volAvg,C_minmaxAvg,P_av,ForwardData,params%rotation_BC) x_scal,params%timeinc, params%rotation_BC)
call MPI_Allreduce(MPI_IN_PLACE,terminallyIll,1,MPI_LOGICAL,MPI_LOR,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,terminallyIll,1,MPI_LOGICAL,MPI_LOR,PETSC_COMM_WORLD,ierr)
ForwardData = .false.
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! stress BC handling ! stress BC handling
F_aim_lastIter = F_aim deltaF_aim = math_mul3333xx33(S, P_av - params%stress_BC)
F_aim = F_aim - math_mul3333xx33(S, ((P_av - params%stress_BC))) ! S = 0.0 for no bc F_aim = F_aim - deltaF_aim
err_stress = maxval(abs(mask_stress * (P_av - params%stress_BC))) ! mask = 0.0 for no bc err_BC = maxval(abs(mask_stress * (P_av - params%stress_BC))) ! mask = 0.0 when no stress bc
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! updated deformation gradient using fix point algorithm of basic scheme ! updated deformation gradient using fix point algorithm of basic scheme
tensorField_real = 0.0_pReal tensorField_real = 0.0_pReal
tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = f_scal tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = f_scal
call utilities_FFTtensorForward() call utilities_FFTtensorForward() ! FFT forward of global "tensorField_real"
err_div = Utilities_divergenceRMS() err_div = Utilities_divergenceRMS() ! divRMS of tensorField_fourier
call utilities_fourierGammaConvolution(math_rotate_backward33(F_aim_lastIter-F_aim,params%rotation_BC)) call utilities_fourierGammaConvolution(math_rotate_backward33(deltaF_aim,params%rotation_BC)) ! convolution of Gamma and tensorField_fourier, with arg
call utilities_FFTtensorBackward() call utilities_FFTtensorBackward() ! FFT backward of global tensorField_fourier
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! constructing residual ! constructing residual
f_scal = tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) f_scal = tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) ! Gamma*P gives correction towards div(P) = 0, so needs to be zero, too
end subroutine BasicPETSc_formResidual end subroutine BasicPETSc_formResidual
@ -413,14 +409,14 @@ subroutine BasicPETSc_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,du
PetscErrorCode :: ierr PetscErrorCode :: ierr
real(pReal) :: & real(pReal) :: &
divTol, & divTol, &
stressTol BCTol
divTol = max(maxval(abs(P_av))*err_div_tolRel,err_div_tolAbs) divTol = max(maxval(abs(P_av))*err_div_tolRel ,err_div_tolAbs)
stressTol = max(maxval(abs(P_av))*err_stress_tolrel,err_stress_tolabs) BCTol = max(maxval(abs(P_av))*err_stress_tolRel,err_stress_tolAbs)
converged: if ((totalIter >= itmin .and. & converged: if ((totalIter >= itmin .and. &
all([ err_div/divTol, & all([ err_div/divTol, &
err_stress/stressTol ] < 1.0_pReal)) & err_BC /BCTol ] < 1.0_pReal)) &
.or. terminallyIll) then .or. terminallyIll) then
reason = 1 reason = 1
elseif (totalIter >= itmax) then converged elseif (totalIter >= itmax) then converged
@ -433,9 +429,9 @@ subroutine BasicPETSc_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,du
! report ! report
write(6,'(1/,a)') ' ... reporting .............................................................' write(6,'(1/,a)') ' ... reporting .............................................................'
write(6,'(1/,a,f12.2,a,es8.2,a,es9.2,a)') ' error divergence = ', & write(6,'(1/,a,f12.2,a,es8.2,a,es9.2,a)') ' error divergence = ', &
err_div/divTol, ' (',err_div,' / m, tol =',divTol,')' err_div/divTol, ' (',err_div,' / m, tol = ',divTol,')'
write(6,'(a,f12.2,a,es8.2,a,es9.2,a)') ' error stress BC = ', & write(6,'(a,f12.2,a,es8.2,a,es9.2,a)') ' error stress BC = ', &
err_stress/stressTol, ' (',err_stress, ' Pa, tol =',stressTol,')' err_BC/BCTol, ' (',err_BC, ' Pa, tol = ',BCTol,')'
write(6,'(/,a)') ' ===========================================================================' write(6,'(/,a)') ' ==========================================================================='
flush(6) flush(6)
@ -443,6 +439,8 @@ end subroutine BasicPETSc_converged
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief forwarding routine !> @brief forwarding routine
!> @details find new boundary conditions and best F estimate for end of current timestep
!> possibly writing restart information, triggering of state increment in DAMASK, and updating of IPcoordinates
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine BasicPETSc_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stress_BC,rotation_BC) subroutine BasicPETSc_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stress_BC,rotation_BC)
use math, only: & use math, only: &
@ -450,9 +448,13 @@ subroutine BasicPETSc_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation
math_rotate_backward33 math_rotate_backward33
use numerics, only: & use numerics, only: &
worldrank worldrank
use homogenization, only: &
materialpoint_F0
use mesh, only: & use mesh, only: &
grid, & grid, &
grid3 grid3
use CPFEM2, only: &
CPFEM_age
use spectral_utilities, only: & use spectral_utilities, only: &
Utilities_calculateRate, & Utilities_calculateRate, &
Utilities_forwardField, & Utilities_forwardField, &
@ -465,6 +467,8 @@ subroutine BasicPETSc_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation
restartWrite restartWrite
implicit none implicit none
logical, intent(in) :: &
guess
real(pReal), intent(in) :: & real(pReal), intent(in) :: &
timeinc_old, & timeinc_old, &
timeinc, & timeinc, &
@ -472,74 +476,78 @@ subroutine BasicPETSc_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation
type(tBoundaryCondition), intent(in) :: & type(tBoundaryCondition), intent(in) :: &
stress_BC, & stress_BC, &
deformation_BC deformation_BC
real(pReal), dimension(3,3), intent(in) :: rotation_BC real(pReal), dimension(3,3), intent(in) ::&
logical, intent(in) :: & rotation_BC
guess
PetscErrorCode :: ierr PetscErrorCode :: ierr
PetscScalar, pointer :: F(:,:,:,:) PetscScalar, dimension(:,:,:,:), pointer :: F
character(len=1024) :: rankStr character(len=32) :: rankStr
call DMDAVecGetArrayF90(da,solution_vec,F,ierr) call DMDAVecGetArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr)
!--------------------------------------------------------------------------------------------------
! restart information for spectral solver
if (restartWrite) then
write(6,'(/,a)') ' writing converged results for restart'
flush(6)
write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'F'//trim(rankStr),size(F)) ! writing deformation gradient field to file
write (777,rec=1) F
close (777)
call IO_write_jobRealFile(777,'F_lastInc'//trim(rankStr),size(F_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lastInc
close (777)
if (worldrank == 0_pInt) then
call IO_write_jobRealFile(777,'F_aimDot',size(F_aimDot))
write (777,rec=1) F_aimDot
close(777)
call IO_write_jobRealFile(777,'C_volAvg',size(C_volAvg))
write (777,rec=1) C_volAvg
close(777)
call IO_write_jobRealFile(777,'C_volAvgLastInc',size(C_volAvgLastInc))
write (777,rec=1) C_volAvgLastInc
close(777)
endif
endif
call utilities_updateIPcoords(F)
if (cutBack) then if (cutBack) then
F_aim = F_aim_lastInc C_volAvg = C_volAvgLastInc ! QUESTION: where is this required?
F = reshape(F_lastInc, [9,grid(1),grid(2),grid3]) C_minMaxAvg = C_minMaxAvgLastInc ! QUESTION: where is this required?
C_volAvg = C_volAvgLastInc
else else
ForwardData = .True. !--------------------------------------------------------------------------------------------------
C_volAvgLastInc = C_volAvg ! restart information for spectral solver
!-------------------------------------------------------------------------------------------------- if (restartWrite) then ! QUESTION: where is this logical properly set?
! calculate rate for aim write(6,'(/,a)') ' writing converged results for restart'
if (deformation_BC%myType=='l') then ! calculate f_aimDot from given L and current F flush(6)
f_aimDot = deformation_BC%maskFloat * math_mul33x33(deformation_BC%values, F_aim)
elseif(deformation_BC%myType=='fdot') then ! f_aimDot is prescribed
f_aimDot = deformation_BC%maskFloat * deformation_BC%values
elseif(deformation_BC%myType=='f') then ! aim at end of load case is prescribed
f_aimDot = deformation_BC%maskFloat * (deformation_BC%values -F_aim)/loadCaseTime
endif
if (guess) f_aimDot = f_aimDot + stress_BC%maskFloat * (F_aim - F_aim_lastInc)/timeinc_old
F_aim_lastInc = F_aim
!-------------------------------------------------------------------------------------------------- if (worldrank == 0_pInt) then
! update coordinates and rate and forward last inc call IO_write_jobRealFile(777,'C_volAvg',size(C_volAvg))
write (777,rec=1) C_volAvg; close(777)
call IO_write_jobRealFile(777,'C_volAvgLastInc',size(C_volAvgLastInc))
write (777,rec=1) C_volAvgLastInc; close(777)
call IO_write_jobRealFile(777,'F_aimDot',size(F_aimDot))
write (777,rec=1) F_aimDot; close(777)
endif
write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'F'//trim(rankStr),size(F)) ! writing deformation gradient field to file
write (777,rec=1) F; close (777)
call IO_write_jobRealFile(777,'F_lastInc'//trim(rankStr),size(F_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lastInc; close (777)
endif
call CPFEM_age() ! age state and kinematics
call utilities_updateIPcoords(F) call utilities_updateIPcoords(F)
Fdot = Utilities_calculateRate(math_rotate_backward33(f_aimDot,rotation_BC), &
timeinc_old,guess,F_lastInc,reshape(F,[3,3,grid(1),grid(2),grid3])) C_volAvgLastInc = C_volAvg
F_lastInc = reshape(F, [3,3,grid(1),grid(2),grid3]) C_minMaxAvgLastInc = C_minMaxAvg
if (guess) then ! QUESTION: better with a = L ? x:y
F_aimDot = stress_BC%maskFloat * (F_aim - F_aim_lastInc)/timeinc_old ! initialize with correction based on last inc
else
F_aimDot = 0.0_pReal
endif ! components of deformation_BC%maskFloat always start out with zero
F_aim_lastInc = F_aim
!--------------------------------------------------------------------------------------------------
! calculate rate for aim
if (deformation_BC%myType=='l') then ! calculate F_aimDot from given L and current F
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * math_mul33x33(deformation_BC%values, F_aim_lastInc)
elseif(deformation_BC%myType=='fdot') then ! F_aimDot is prescribed
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * deformation_BC%values
elseif (deformation_BC%myType=='f') then ! aim at end of load case is prescribed
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * (deformation_BC%values - F_aim_lastInc)/loadCaseTime
endif endif
F_aim = F_aim + f_aimDot * timeinc
Fdot = Utilities_calculateRate(guess, &
F_lastInc,reshape(F,[3,3,grid(1),grid(2),grid3]),timeinc_old, &
math_rotate_backward33(F_aimDot,rotation_BC))
F_lastInc = reshape(F, [3,3,grid(1),grid(2),grid3]) ! winding F forward
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3]) ! set starting condition for materialpoint_stressAndItsTangent
endif
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! update local deformation gradient ! update average and local deformation gradients
F = reshape(Utilities_forwardField(timeinc,F_lastInc,Fdot, & ! ensure that it matches rotated F_aim F_aim = F_aim_lastInc + F_aimDot * timeinc
F = reshape(Utilities_forwardField(timeinc,F_lastInc,Fdot, & ! estimate of F at end of time+timeinc that matches rotated F_aim on average
math_rotate_backward33(F_aim,rotation_BC)),[9,grid(1),grid(2),grid3]) math_rotate_backward33(F_aim,rotation_BC)),[9,grid(1),grid(2),grid3])
call DMDAVecRestoreArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr) call DMDAVecRestoreArrayF90(da,solution_vec,F,ierr); CHKERRQ(ierr)

View File

@ -43,7 +43,7 @@ module spectral_mech_Polarisation
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! stress, stiffness and compliance average etc. ! stress, stiffness and compliance average etc.
real(pReal), private, dimension(3,3) :: & real(pReal), private, dimension(3,3) :: &
F_aimDot, & !< assumed rate of average deformation gradient F_aimDot = 0.0_pReal, & !< assumed rate of average deformation gradient
F_aim = math_I3, & !< current prescribed deformation gradient F_aim = math_I3, & !< current prescribed deformation gradient
F_aim_lastInc = math_I3, & !< previous average deformation gradient F_aim_lastInc = math_I3, & !< previous average deformation gradient
F_av = 0.0_pReal, & !< average incompatible def grad field F_av = 0.0_pReal, & !< average incompatible def grad field
@ -54,6 +54,7 @@ module spectral_mech_Polarisation
C_volAvg = 0.0_pReal, & !< current volume average stiffness C_volAvg = 0.0_pReal, & !< current volume average stiffness
C_volAvgLastInc = 0.0_pReal, & !< previous volume average stiffness C_volAvgLastInc = 0.0_pReal, & !< previous volume average stiffness
C_minMaxAvg = 0.0_pReal, & !< current (min+max)/2 stiffness C_minMaxAvg = 0.0_pReal, & !< current (min+max)/2 stiffness
C_minMaxAvgLastInc = 0.0_pReal, & !< previous (min+max)/2 stiffness
S = 0.0_pReal, & !< current compliance (filled up with zeros) S = 0.0_pReal, & !< current compliance (filled up with zeros)
C_scale = 0.0_pReal, & C_scale = 0.0_pReal, &
S_scale = 0.0_pReal S_scale = 0.0_pReal
@ -62,7 +63,7 @@ module spectral_mech_Polarisation
err_BC, & !< deviation from stress BC err_BC, & !< deviation from stress BC
err_curl, & !< RMS of curl of F err_curl, & !< RMS of curl of F
err_div !< RMS of div of P err_div !< RMS of div of P
logical, private :: ForwardData
integer(pInt), private :: & integer(pInt), private :: &
totalIter = 0_pInt !< total iteration in current increment totalIter = 0_pInt !< total iteration in current increment
@ -80,7 +81,7 @@ module spectral_mech_Polarisation
contains contains
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief allocates all neccessary fields and fills them with data, potentially from restart info !> @brief allocates all necessary fields and fills them with data, potentially from restart info
!> @todo use sourced allocation, e.g. allocate(Fdot,source = F_lastInc) !> @todo use sourced allocation, e.g. allocate(Fdot,source = F_lastInc)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine Polarisation_init subroutine Polarisation_init
@ -102,12 +103,15 @@ subroutine Polarisation_init
use numerics, only: & use numerics, only: &
worldrank, & worldrank, &
worldsize worldsize
use homogenization, only: &
materialpoint_F0
use DAMASK_interface, only: & use DAMASK_interface, only: &
getSolverJobName getSolverJobName
use spectral_utilities, only: & use spectral_utilities, only: &
Utilities_constitutiveResponse, & Utilities_constitutiveResponse, &
Utilities_updateGamma, & Utilities_updateGamma, &
Utilities_updateIPcoords Utilities_updateIPcoords, &
wgt
use mesh, only: & use mesh, only: &
grid, & grid, &
grid3 grid3
@ -120,7 +124,11 @@ subroutine Polarisation_init
temp33_Real = 0.0_pReal temp33_Real = 0.0_pReal
PetscErrorCode :: ierr PetscErrorCode :: ierr
PetscScalar, pointer, dimension(:,:,:,:) :: xx_psc, F, F_tau PetscScalar, pointer, dimension(:,:,:,:) :: &
FandF_tau, & ! overall pointer to solution data
F, & ! specific (sub)pointer
F_tau ! specific (sub)pointer
integer(pInt), dimension(:), allocatable :: localK integer(pInt), dimension(:), allocatable :: localK
integer(pInt) :: proc integer(pInt) :: proc
character(len=1024) :: rankStr character(len=1024) :: rankStr
@ -164,78 +172,69 @@ subroutine Polarisation_init
grid(1),grid(2),localK, & ! local grid grid(1),grid(2),localK, & ! local grid
da,ierr) ! handle, error da,ierr) ! handle, error
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) call SNESSetDM(snes,da,ierr); CHKERRQ(ierr) ! connect snes to da
call DMCreateGlobalVector(da,solution_vec,ierr); CHKERRQ(ierr) call DMCreateGlobalVector(da,solution_vec,ierr); CHKERRQ(ierr) ! global solution vector (grid x 9, i.e. every def grad tensor)
call DMDASNESSetFunctionLocal(da,INSERT_VALUES,Polarisation_formResidual,PETSC_NULL_OBJECT,ierr) call DMDASNESSetFunctionLocal(da,INSERT_VALUES,Polarisation_formResidual,PETSC_NULL_OBJECT,ierr) ! residual vector of same shape as solution vector
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetConvergenceTest(snes,Polarisation_converged,PETSC_NULL_OBJECT,PETSC_NULL_FUNCTION,ierr) call SNESSetConvergenceTest(snes,Polarisation_converged,PETSC_NULL_OBJECT,PETSC_NULL_FUNCTION,ierr) ! specify custom convergence check function "_converged"
CHKERRQ(ierr) CHKERRQ(ierr)
call SNESSetFromOptions(snes,ierr); CHKERRQ(ierr) call SNESSetFromOptions(snes,ierr); CHKERRQ(ierr) ! pull it all together with additional cli arguments
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! init fields ! init fields
call DMDAVecGetArrayF90(da,solution_vec,xx_psc,ierr); CHKERRQ(ierr) ! places pointer xx_psc on PETSc data call DMDAVecGetArrayF90(da,solution_vec,FandF_tau,ierr); CHKERRQ(ierr) ! places pointer on PETSc data
F => xx_psc(0:8,:,:,:) F => FandF_tau( 0: 8,:,:,:)
F_tau => xx_psc(9:17,:,:,:) F_tau => FandF_tau( 9:17,:,:,:)
restart: if (restartInc > 1_pInt) then restart: if (restartInc > 0_pInt) then
if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0) & if (iand(debug_level(debug_spectral),debug_spectralRestart) /= 0) then
write(6,'(/,a,'//IO_intOut(restartInc-1_pInt)//',a)') & write(6,'(/,a,'//IO_intOut(restartInc)//',a)') &
'reading values of increment ', restartInc - 1_pInt, ' from file' 'reading values of increment ', restartInc, ' from file'
flush(6) flush(6)
endif
write(rankStr,'(a1,i0)')'_',worldrank write(rankStr,'(a1,i0)')'_',worldrank
call IO_read_realFile(777,'F'//trim(rankStr),trim(getSolverJobName()),size(F)) call IO_read_realFile(777,'F'//trim(rankStr),trim(getSolverJobName()),size(F))
read (777,rec=1) F read (777,rec=1) F; close (777)
close (777)
call IO_read_realFile(777,'F_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lastInc)) call IO_read_realFile(777,'F_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_lastInc))
read (777,rec=1) F_lastInc read (777,rec=1) F_lastInc; close (777)
close (777)
call IO_read_realFile(777,'F_tau'//trim(rankStr),trim(getSolverJobName()),size(F_tau)) call IO_read_realFile(777,'F_tau'//trim(rankStr),trim(getSolverJobName()),size(F_tau))
read (777,rec=1) F_tau read (777,rec=1) F_tau; close (777)
close (777) call IO_read_realFile(777,'F_tau_lastInc'//trim(rankStr),trim(getSolverJobName()),size(F_tau_lastInc))
call IO_read_realFile(777,'F_tau_lastInc'//trim(rankStr),& read (777,rec=1) F_tau_lastInc; close (777)
trim(getSolverJobName()),size(F_tau_lastInc)) call IO_read_realFile(777,'F_aimDot',trim(getSolverJobName()),size(F_aimDot))
read (777,rec=1) F_tau_lastInc read (777,rec=1) F_aimDot; close (777)
close (777) F_aim = reshape(sum(sum(sum(F,dim=4),dim=3),dim=2) * wgt, [3,3]) ! average of F
call IO_read_realFile(777,'F_aim', trim(getSolverJobName()),size(F_aim)) F_aim_lastInc = sum(sum(sum(F_lastInc,dim=5),dim=4),dim=3) * wgt ! average of F_lastInc
read (777,rec=1) F_aim elseif (restartInc == 0_pInt) then restart
close (777)
call IO_read_realFile(777,'F_aim_lastInc', trim(getSolverJobName()),size(F_aim_lastInc))
read (777,rec=1) F_aim_lastInc
close (777)
call IO_read_realFile(777,'F_aimDot',trim(getSolverJobName()),size(f_aimDot))
read (777,rec=1) f_aimDot
close (777)
elseif (restartInc == 1_pInt) then restart
F_lastInc = spread(spread(spread(math_I3,3,grid(1)),4,grid(2)),5,grid3) ! initialize to identity F_lastInc = spread(spread(spread(math_I3,3,grid(1)),4,grid(2)),5,grid3) ! initialize to identity
F = reshape(F_lastInc,[9,grid(1),grid(2),grid3]) F = reshape(F_lastInc,[9,grid(1),grid(2),grid3])
F_tau = 2.0_pReal* F F_tau = 2.0_pReal*F
F_tau_lastInc = 2.0_pReal*F_lastInc F_tau_lastInc = 2.0_pReal*F_lastInc
endif restart endif restart
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3]) ! set starting condition for materialpoint_stressAndItsTangent
call Utilities_updateIPcoords(reshape(F,shape(F_lastInc))) call Utilities_updateIPcoords(reshape(F,shape(F_lastInc)))
call Utilities_constitutiveResponse(F_lastInc, reshape(F,shape(F_lastInc)), & call Utilities_constitutiveResponse(P,temp33_Real,C_volAvg,C_minMaxAvg, & ! stress field, stress avg, global average of stiffness and (min+max)/2
0.0_pReal,P,C_volAvg,C_minMaxAvg,temp33_Real,.false.,math_I3) reshape(F,shape(F_lastInc)), & ! target F
0.0_pReal, & ! time increment
math_I3) ! no rotation of boundary condition
nullify(F) nullify(F)
nullify(F_tau) nullify(F_tau)
call DMDAVecRestoreArrayF90(da,solution_vec,xx_psc,ierr); CHKERRQ(ierr) ! write data back to PETSc call DMDAVecRestoreArrayF90(da,solution_vec,FandF_tau,ierr); CHKERRQ(ierr) ! write data back to PETSc
restartRead: if (restartInc > 1_pInt) then restartRead: if (restartInc > 0_pInt) then
if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0 .and. worldrank == 0_pInt) & if (iand(debug_level(debug_spectral),debug_spectralRestart)/= 0 .and. worldrank == 0_pInt) &
write(6,'(/,a,'//IO_intOut(restartInc-1_pInt)//',a)') & write(6,'(/,a,'//IO_intOut(restartInc)//',a)') &
'reading more values of increment', restartInc - 1_pInt, 'from file' 'reading more values of increment ', restartInc, ' from file'
flush(6) flush(6)
call IO_read_realFile(777,'C_volAvg',trim(getSolverJobName()),size(C_volAvg)) call IO_read_realFile(777,'C_volAvg',trim(getSolverJobName()),size(C_volAvg))
read (777,rec=1) C_volAvg read (777,rec=1) C_volAvg; close (777)
close (777)
call IO_read_realFile(777,'C_volAvgLastInc',trim(getSolverJobName()),size(C_volAvgLastInc)) call IO_read_realFile(777,'C_volAvgLastInc',trim(getSolverJobName()),size(C_volAvgLastInc))
read (777,rec=1) C_volAvgLastInc read (777,rec=1) C_volAvgLastInc; close (777)
close (777)
call IO_read_realFile(777,'C_ref',trim(getSolverJobName()),size(C_minMaxAvg)) call IO_read_realFile(777,'C_ref',trim(getSolverJobName()),size(C_minMaxAvg))
read (777,rec=1) C_minMaxAvg read (777,rec=1) C_minMaxAvg; close (777)
close (777)
endif restartRead endif restartRead
call Utilities_updateGamma(C_minMaxAvg,.True.) call Utilities_updateGamma(C_minMaxAvg,.true.)
C_scale = C_minMaxAvg C_scale = C_minMaxAvg
S_scale = math_invSym3333(C_minMaxAvg) S_scale = math_invSym3333(C_minMaxAvg)
@ -245,8 +244,7 @@ end subroutine Polarisation_init
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief solution for the Polarisation scheme with internal iterations !> @brief solution for the Polarisation scheme with internal iterations
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
type(tSolutionState) function & type(tSolutionState) function Polarisation_solution(incInfoIn,timeinc,timeinc_old,stress_BC,rotation_BC)
Polarisation_solution(incInfoIn,timeinc,timeinc_old,stress_BC,rotation_BC)
use IO, only: & use IO, only: &
IO_error IO_error
use numerics, only: & use numerics, only: &
@ -265,13 +263,13 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! input data for solution ! input data for solution
real(pReal), intent(in) :: &
timeinc, & !< increment in time for current solution
timeinc_old !< increment in time of last increment
type(tBoundaryCondition), intent(in) :: &
stress_BC
character(len=*), intent(in) :: & character(len=*), intent(in) :: &
incInfoIn incInfoIn
real(pReal), intent(in) :: &
timeinc, & !< increment time for current solution
timeinc_old !< increment time of last successful increment
type(tBoundaryCondition), intent(in) :: &
stress_BC
real(pReal), dimension(3,3), intent(in) :: rotation_BC real(pReal), dimension(3,3), intent(in) :: rotation_BC
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -304,18 +302,17 @@ type(tSolutionState) function &
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! solve BVP ! solve BVP
call SNESSolve(snes,PETSC_NULL_OBJECT,solution_vec,ierr) call SNESSolve(snes,PETSC_NULL_OBJECT,solution_vec,ierr); CHKERRQ(ierr)
CHKERRQ(ierr)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! check convergence ! check convergence
call SNESGetConvergedReason(snes,reason,ierr) call SNESGetConvergedReason(snes,reason,ierr); CHKERRQ(ierr)
CHKERRQ(ierr)
Polarisation_solution%converged = reason > 0
Polarisation_solution%iterationsNeeded = totalIter
Polarisation_solution%termIll = terminallyIll Polarisation_solution%termIll = terminallyIll
terminallyIll = .false. terminallyIll = .false.
if (reason == -4) call IO_error(893_pInt) if (reason == -4) call IO_error(893_pInt) ! MPI error
if (reason < 1) Polarisation_solution%converged = .false.
Polarisation_solution%iterationsNeeded = totalIter
end function Polarisation_solution end function Polarisation_solution
@ -330,8 +327,8 @@ subroutine Polarisation_formResidual(in,x_scal,f_scal,dummy,ierr)
polarAlpha, & polarAlpha, &
polarBeta polarBeta
use mesh, only: & use mesh, only: &
grid3, & grid, &
grid grid3
use IO, only: & use IO, only: &
IO_intOut IO_intOut
use math, only: & use math, only: &
@ -340,6 +337,10 @@ subroutine Polarisation_formResidual(in,x_scal,f_scal,dummy,ierr)
math_mul3333xx33, & math_mul3333xx33, &
math_invSym3333, & math_invSym3333, &
math_mul33x33 math_mul33x33
use debug, only: &
debug_level, &
debug_spectral, &
debug_spectralRotation
use spectral_utilities, only: & use spectral_utilities, only: &
wgt, & wgt, &
tensorField_real, & tensorField_real, &
@ -349,27 +350,17 @@ subroutine Polarisation_formResidual(in,x_scal,f_scal,dummy,ierr)
Utilities_constitutiveResponse, & Utilities_constitutiveResponse, &
Utilities_divergenceRMS, & Utilities_divergenceRMS, &
Utilities_curlRMS Utilities_curlRMS
use debug, only: &
debug_level, &
debug_spectral, &
debug_spectralRotation
use homogenization, only: & use homogenization, only: &
materialpoint_dPdF materialpoint_dPdF
use FEsolving, only: & use FEsolving, only: &
terminallyIll terminallyIll
implicit none implicit none
!-------------------------------------------------------------------------------------------------- DMDALocalInfo, dimension(DMDA_LOCAL_INFO_SIZE) :: in
! strange syntax in the next line because otherwise macros expand beyond 132 character limit PetscScalar, &
DMDALocalInfo, dimension(& target, dimension(3,3,2, XG_RANGE,YG_RANGE,ZG_RANGE), intent(in) :: x_scal
DMDA_LOCAL_INFO_SIZE) :: & PetscScalar, &
in target, dimension(3,3,2, X_RANGE, Y_RANGE, Z_RANGE), intent(out) :: f_scal
PetscScalar, target, dimension(3,3,2, &
XG_RANGE,YG_RANGE,ZG_RANGE), intent(in) :: &
x_scal
PetscScalar, target, dimension(3,3,2, &
X_RANGE,Y_RANGE,Z_RANGE), intent(out) :: &
f_scal
PetscScalar, pointer, dimension(:,:,:,:,:) :: & PetscScalar, pointer, dimension(:,:,:,:,:) :: &
F, & F, &
F_tau, & F_tau, &
@ -392,28 +383,28 @@ subroutine Polarisation_formResidual(in,x_scal,f_scal,dummy,ierr)
F_tau => x_scal(1:3,1:3,2,& F_tau => x_scal(1:3,1:3,2,&
XG_RANGE,YG_RANGE,ZG_RANGE) XG_RANGE,YG_RANGE,ZG_RANGE)
residual_F => f_scal(1:3,1:3,1,& residual_F => f_scal(1:3,1:3,1,&
X_RANGE,Y_RANGE,Z_RANGE) X_RANGE, Y_RANGE, Z_RANGE)
residual_F_tau => f_scal(1:3,1:3,2,& residual_F_tau => f_scal(1:3,1:3,2,&
X_RANGE,Y_RANGE,Z_RANGE) X_RANGE, Y_RANGE, Z_RANGE)
call SNESGetNumberFunctionEvals(snes,nfuncs,ierr); CHKERRQ(ierr)
call SNESGetIterationNumber(snes,PETScIter,ierr); CHKERRQ(ierr)
F_av = sum(sum(sum(F,dim=5),dim=4),dim=3) * wgt F_av = sum(sum(sum(F,dim=5),dim=4),dim=3) * wgt
call MPI_Allreduce(MPI_IN_PLACE,F_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,F_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
if(nfuncs== 0 .and. PETScIter == 0) totalIter = -1_pInt ! new increment call SNESGetNumberFunctionEvals(snes,nfuncs,ierr); CHKERRQ(ierr)
newIteration: if(totalIter <= PETScIter) then call SNESGetIterationNumber(snes,PETScIter,ierr); CHKERRQ(ierr)
if (nfuncs == 0 .and. PETScIter == 0) totalIter = -1_pInt ! new increment
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report begin of new iteration ! begin of new iteration
newIteration: if (totalIter <= PETScIter) then
totalIter = totalIter + 1_pInt totalIter = totalIter + 1_pInt
write(6,'(1x,a,3(a,'//IO_intOut(itmax)//'))') trim(incInfo), & write(6,'(1x,a,3(a,'//IO_intOut(itmax)//'))') &
' @ Iteration ', itmin, '≤',totalIter, '≤', itmax trim(incInfo), ' @ Iteration ', itmin, '≤',totalIter, '≤', itmax
if (iand(debug_level(debug_spectral),debug_spectralRotation) /= 0) & if (iand(debug_level(debug_spectral),debug_spectralRotation) /= 0) &
write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') ' deformation gradient aim (lab) =', & write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') &
math_transpose33(math_rotate_backward33(F_aim,params%rotation_BC)) ' deformation gradient aim (lab) =', math_transpose33(math_rotate_backward33(F_aim,params%rotation_BC))
write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') ' deformation gradient aim =', & write(6,'(/,a,/,3(3(f12.7,1x)/))',advance='no') &
math_transpose33(F_aim) ' deformation gradient aim =', math_transpose33(F_aim)
flush(6) flush(6)
endif newIteration endif newIteration
@ -440,18 +431,16 @@ subroutine Polarisation_formResidual(in,x_scal,f_scal,dummy,ierr)
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! evaluate constitutive response ! evaluate constitutive response
P_avLastEval = P_av P_avLastEval = P_av
call Utilities_constitutiveResponse(F_lastInc,F - residual_F_tau/polarBeta,params%timeinc, & call Utilities_constitutiveResponse(residual_F,P_av,C_volAvg,C_minMaxAvg, &
residual_F,C_volAvg,C_minMaxAvg,P_av,ForwardData,params%rotation_BC) F - residual_F_tau/polarBeta,params%timeinc,params%rotation_BC)
call MPI_Allreduce(MPI_IN_PLACE,terminallyIll,1,MPI_LOGICAL,MPI_LOR,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,terminallyIll,1,MPI_LOGICAL,MPI_LOR,PETSC_COMM_WORLD,ierr)
ForwardData = .False.
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! calculate divergence ! calculate divergence
tensorField_real = 0.0_pReal tensorField_real = 0.0_pReal
tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = residual_F tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = residual_F !< stress field in disguise
call utilities_FFTtensorForward() call utilities_FFTtensorForward()
err_div = Utilities_divergenceRMS() err_div = Utilities_divergenceRMS() !< root mean squared error in divergence of stress
call utilities_FFTtensorBackward()
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! constructing residual ! constructing residual
@ -471,8 +460,11 @@ subroutine Polarisation_formResidual(in,x_scal,f_scal,dummy,ierr)
tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = F tensorField_real(1:3,1:3,1:grid(1),1:grid(2),1:grid3) = F
call utilities_FFTtensorForward() call utilities_FFTtensorForward()
err_curl = Utilities_curlRMS() err_curl = Utilities_curlRMS()
call utilities_FFTtensorBackward()
nullify(F)
nullify(F_tau)
nullify(residual_F)
nullify(residual_F_tau)
end subroutine Polarisation_formResidual end subroutine Polarisation_formResidual
@ -487,8 +479,8 @@ subroutine Polarisation_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,
err_div_tolAbs, & err_div_tolAbs, &
err_curl_tolRel, & err_curl_tolRel, &
err_curl_tolAbs, & err_curl_tolAbs, &
err_stress_tolAbs, & err_stress_tolRel, &
err_stress_tolRel err_stress_tolAbs
use math, only: & use math, only: &
math_mul3333xx33 math_mul3333xx33
use FEsolving, only: & use FEsolving, only: &
@ -507,24 +499,24 @@ subroutine Polarisation_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,
real(pReal) :: & real(pReal) :: &
curlTol, & curlTol, &
divTol, & divTol, &
BC_tol BCTol
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! stress BC handling ! stress BC handling
F_aim = F_aim - math_mul3333xx33(S, ((P_av - params%stress_BC))) ! S = 0.0 for no bc F_aim = F_aim - math_mul3333xx33(S, ((P_av - params%stress_BC))) ! S = 0.0 for no bc
err_BC = maxval(abs((-mask_stress+1.0_pReal)*math_mul3333xx33(C_scale,F_aim-F_av) + & err_BC = maxval(abs((1.0_pReal-mask_stress) * math_mul3333xx33(C_scale,F_aim-F_av) + &
mask_stress *(P_av - params%stress_BC))) ! mask = 0.0 for no bc mask_stress * (P_av-params%stress_BC))) ! mask = 0.0 for no bc
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! error calculation ! error calculation
curlTol = max(maxval(abs(F_aim-math_I3))*err_curl_tolRel,err_curl_tolAbs) curlTol = max(maxval(abs(F_aim-math_I3))*err_curl_tolRel ,err_curl_tolAbs)
divTol = max(maxval(abs(P_av)) *err_div_tolRel,err_div_tolAbs) divTol = max(maxval(abs(P_av)) *err_div_tolRel ,err_div_tolAbs)
BC_tol = max(maxval(abs(P_av)) *err_stress_tolrel,err_stress_tolabs) BCTol = max(maxval(abs(P_av)) *err_stress_tolRel,err_stress_tolAbs)
converged: if ((totalIter >= itmin .and. & converged: if ((totalIter >= itmin .and. &
all([ err_div/divTol, & all([ err_div /divTol, &
err_curl/curlTol, & err_curl/curlTol, &
err_BC/BC_tol ] < 1.0_pReal)) & err_BC /BCTol ] < 1.0_pReal)) &
.or. terminallyIll) then .or. terminallyIll) then
reason = 1 reason = 1
elseif (totalIter >= itmax) then converged elseif (totalIter >= itmax) then converged
@ -536,12 +528,12 @@ subroutine Polarisation_converged(snes_local,PETScIter,xnorm,snorm,fnorm,reason,
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! report ! report
write(6,'(1/,a)') ' ... reporting .............................................................' write(6,'(1/,a)') ' ... reporting .............................................................'
write(6,'(/,a,f12.2,a,es8.2,a,es9.2,a)') ' error curl = ', & write(6,'(/,a,f12.2,a,es8.2,a,es9.2,a)') ' error divergence = ', &
err_curl/curlTol,' (',err_curl,' -, tol =',curlTol,')' err_div/divTol, ' (',err_div, ' / m, tol = ',divTol,')'
write(6,' (a,f12.2,a,es8.2,a,es9.2,a)') ' error divergence = ', & write(6, '(a,f12.2,a,es8.2,a,es9.2,a)') ' error curl = ', &
err_div/divTol, ' (',err_div, ' / m, tol =',divTol,')' err_curl/curlTol,' (',err_curl,' -, tol = ',curlTol,')'
write(6,' (a,f12.2,a,es8.2,a,es9.2,a)') ' error BC = ', & write(6, '(a,f12.2,a,es8.2,a,es9.2,a)') ' error BC = ', &
err_BC/BC_tol, ' (',err_BC, ' Pa, tol =',BC_tol,')' err_BC/BCTol, ' (',err_BC, ' Pa, tol = ',BCTol,')'
write(6,'(/,a)') ' ===========================================================================' write(6,'(/,a)') ' ==========================================================================='
flush(6) flush(6)
@ -549,6 +541,8 @@ end subroutine Polarisation_converged
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief forwarding routine !> @brief forwarding routine
!> @details find new boundary conditions and best F estimate for end of current timestep
!> possibly writing restart information, triggering of state increment in DAMASK, and updating of IPcoordinates
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine Polarisation_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stress_BC,rotation_BC) subroutine Polarisation_forward(guess,timeinc,timeinc_old,loadCaseTime,deformation_BC,stress_BC,rotation_BC)
use math, only: & use math, only: &
@ -558,9 +552,13 @@ subroutine Polarisation_forward(guess,timeinc,timeinc_old,loadCaseTime,deformati
math_rotate_backward33 math_rotate_backward33
use numerics, only: & use numerics, only: &
worldrank worldrank
use homogenization, only: &
materialpoint_F0
use mesh, only: & use mesh, only: &
grid3, & grid, &
grid grid3
use CPFEM2, only: &
CPFEM_age
use spectral_utilities, only: & use spectral_utilities, only: &
Utilities_calculateRate, & Utilities_calculateRate, &
Utilities_forwardField, & Utilities_forwardField, &
@ -573,6 +571,8 @@ subroutine Polarisation_forward(guess,timeinc,timeinc_old,loadCaseTime,deformati
restartWrite restartWrite
implicit none implicit none
logical, intent(in) :: &
guess
real(pReal), intent(in) :: & real(pReal), intent(in) :: &
timeinc_old, & timeinc_old, &
timeinc, & timeinc, &
@ -580,111 +580,112 @@ subroutine Polarisation_forward(guess,timeinc,timeinc_old,loadCaseTime,deformati
type(tBoundaryCondition), intent(in) :: & type(tBoundaryCondition), intent(in) :: &
stress_BC, & stress_BC, &
deformation_BC deformation_BC
real(pReal), dimension(3,3), intent(in) :: rotation_BC real(pReal), dimension(3,3), intent(in) ::&
logical, intent(in) :: & rotation_BC
guess
PetscErrorCode :: ierr PetscErrorCode :: ierr
PetscScalar, dimension(:,:,:,:), pointer :: xx_psc, F, F_tau PetscScalar, dimension(:,:,:,:), pointer :: FandF_tau, F, F_tau
integer(pInt) :: i, j, k integer(pInt) :: i, j, k
real(pReal), dimension(3,3) :: F_lambda33 real(pReal), dimension(3,3) :: F_lambda33
character(len=1024) :: rankStr character(len=32) :: rankStr
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! update coordinates and rate and forward last inc ! update coordinates and rate and forward last inc
call DMDAVecGetArrayF90(da,solution_vec,xx_psc,ierr) call DMDAVecGetArrayF90(da,solution_vec,FandF_tau,ierr); CHKERRQ(ierr)
F => xx_psc(0:8,:,:,:) F => FandF_tau( 0: 8,:,:,:)
F_tau => xx_psc(9:17,:,:,:) F_tau => FandF_tau( 9:17,:,:,:)
if (restartWrite) then
write(6,'(/,a)') ' writing converged results for restart'
flush(6)
write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'F'//trim(rankStr),size(F)) ! writing deformation gradient field to file
write (777,rec=1) F
close (777)
call IO_write_jobRealFile(777,'F_lastInc'//trim(rankStr),size(F_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lastInc
close (777)
call IO_write_jobRealFile(777,'F_tau'//trim(rankStr),size(F_tau)) ! writing deformation gradient field to file
write (777,rec=1) F_tau
close (777)
call IO_write_jobRealFile(777,'F_tau_lastInc'//trim(rankStr),size(F_tau_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_tau_lastInc
close (777)
if (worldrank == 0_pInt) then
call IO_write_jobRealFile(777,'F_aim',size(F_aim))
write (777,rec=1) F_aim
close(777)
call IO_write_jobRealFile(777,'F_aim_lastInc',size(F_aim_lastInc))
write (777,rec=1) F_aim_lastInc
close (777)
call IO_write_jobRealFile(777,'F_aimDot',size(F_aimDot))
write (777,rec=1) F_aimDot
close(777)
call IO_write_jobRealFile(777,'C_volAvg',size(C_volAvg))
write (777,rec=1) C_volAvg
close(777)
call IO_write_jobRealFile(777,'C_volAvgLastInc',size(C_volAvgLastInc))
write (777,rec=1) C_volAvgLastInc
close(777)
endif
endif
call utilities_updateIPcoords(F)
if (cutBack) then if (cutBack) then
F_aim = F_aim_lastInc C_volAvg = C_volAvgLastInc ! QUESTION: where is this required?
F_tau= reshape(F_tau_lastInc,[9,grid(1),grid(2),grid3]) C_minMaxAvg = C_minMaxAvgLastInc ! QUESTION: where is this required?
F = reshape(F_lastInc, [9,grid(1),grid(2),grid3])
C_volAvg = C_volAvgLastInc
else else
ForwardData = .True. !--------------------------------------------------------------------------------------------------
C_volAvgLastInc = C_volAvg ! restart information for spectral solver
!-------------------------------------------------------------------------------------------------- if (restartWrite) then ! QUESTION: where is this logical properly set?
! calculate rate for aim write(6,'(/,a)') ' writing converged results for restart'
if (deformation_BC%myType=='l') then ! calculate f_aimDot from given L and current F flush(6)
f_aimDot = deformation_BC%maskFloat * math_mul33x33(deformation_BC%values, F_aim)
elseif(deformation_BC%myType=='fdot') then ! f_aimDot is prescribed
f_aimDot = deformation_BC%maskFloat * deformation_BC%values
elseif(deformation_BC%myType=='f') then ! aim at end of load case is prescribed
f_aimDot = deformation_BC%maskFloat * (deformation_BC%values -F_aim)/loadCaseTime
endif
if (guess) f_aimDot = f_aimDot + stress_BC%maskFloat * (F_aim - F_aim_lastInc)/timeinc_old
F_aim_lastInc = F_aim
!-------------------------------------------------------------------------------------------------- if (worldrank == 0_pInt) then
! update coordinates and rate and forward last inc call IO_write_jobRealFile(777,'C_volAvg',size(C_volAvg))
write (777,rec=1) C_volAvg; close(777)
call IO_write_jobRealFile(777,'C_volAvgLastInc',size(C_volAvgLastInc))
write (777,rec=1) C_volAvgLastInc; close(777)
call IO_write_jobRealFile(777,'F_aimDot',size(F_aimDot))
write (777,rec=1) F_aimDot; close(777)
endif
write(rankStr,'(a1,i0)')'_',worldrank
call IO_write_jobRealFile(777,'F'//trim(rankStr),size(F)) ! writing deformation gradient field to file
write (777,rec=1) F; close (777)
call IO_write_jobRealFile(777,'F_lastInc'//trim(rankStr),size(F_lastInc)) ! writing F_lastInc field to file
write (777,rec=1) F_lastInc; close (777)
call IO_write_jobRealFile(777,'F_tau'//trim(rankStr),size(F_tau)) ! writing deformation gradient field to file
write (777,rec=1) F_tau; close (777)
call IO_write_jobRealFile(777,'F_tau_lastInc'//trim(rankStr),size(F_tau_lastInc)) ! writing F_tau_lastInc field to file
write (777,rec=1) F_tau_lastInc; close (777)
endif
call CPFEM_age() ! age state and kinematics
call utilities_updateIPcoords(F) call utilities_updateIPcoords(F)
Fdot = Utilities_calculateRate(math_rotate_backward33(f_aimDot,rotation_BC), &
timeinc_old,guess,F_lastInc, & C_volAvgLastInc = C_volAvg
reshape(F,[3,3,grid(1),grid(2),grid3])) C_minMaxAvgLastInc = C_minMaxAvg
F_tauDot = Utilities_calculateRate(math_rotate_backward33(2.0_pReal*f_aimDot,rotation_BC), &
timeinc_old,guess,F_tau_lastInc, & if (guess) then ! QUESTION: better with a = L ? x:y
reshape(F_tau,[3,3,grid(1),grid(2),grid3])) F_aimDot = stress_BC%maskFloat * (F_aim - F_aim_lastInc)/timeinc_old ! initialize with correction based on last inc
F_lastInc = reshape(F, [3,3,grid(1),grid(2),grid3]) else
F_tau_lastInc = reshape(F_tau,[3,3,grid(1),grid(2),grid3]) F_aimDot = 0.0_pReal
endif
F_aim_lastInc = F_aim
!--------------------------------------------------------------------------------------------------
! calculate rate for aim
if (deformation_BC%myType=='l') then ! calculate F_aimDot from given L and current F
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * math_mul33x33(deformation_BC%values, F_aim_lastInc)
elseif(deformation_BC%myType=='fdot') then ! F_aimDot is prescribed
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * deformation_BC%values
elseif (deformation_BC%myType=='f') then ! aim at end of load case is prescribed
F_aimDot = &
F_aimDot + deformation_BC%maskFloat * (deformation_BC%values - F_aim_lastInc)/loadCaseTime
endif endif
F_aim = F_aim + f_aimDot * timeinc
Fdot = Utilities_calculateRate(guess, &
F_lastInc,reshape(F,[3,3,grid(1),grid(2),grid3]),timeinc_old, &
math_rotate_backward33(F_aimDot,rotation_BC))
F_tauDot = Utilities_calculateRate(guess, &
F_tau_lastInc,reshape(F_tau,[3,3,grid(1),grid(2),grid3]), timeinc_old, &
math_rotate_backward33(F_aimDot,rotation_BC))
F_lastInc = reshape(F, [3,3,grid(1),grid(2),grid3]) ! winding F forward
F_tau_lastInc = reshape(F_tau, [3,3,grid(1),grid(2),grid3]) ! winding F_tau forward
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3]) ! set starting condition for materialpoint_stressAndItsTangent
endif
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! update local deformation gradient ! update average and local deformation gradients
F = reshape(Utilities_forwardField(timeinc,F_lastInc,Fdot, & ! ensure that it matches rotated F_aim F_aim = F_aim_lastInc + F_aimDot * timeinc
math_rotate_backward33(F_aim,rotation_BC)), &
F = reshape(Utilities_forwardField(timeinc,F_lastInc,Fdot, & ! estimate of F at end of time+timeinc that matches rotated F_aim on average
math_rotate_backward33(F_aim,rotation_BC)),&
[9,grid(1),grid(2),grid3]) [9,grid(1),grid(2),grid3])
F_tau = reshape(Utilities_forwardField(timeinc,F_tau_lastInc,F_taudot), & ! does not have any average value as boundary condition if (guess) then
[9,grid(1),grid(2),grid3]) F_tau = reshape(Utilities_forwardField(timeinc,F_tau_lastInc,F_taudot), &
if (.not. guess) then ! large strain forwarding [9,grid(1),grid(2),grid3]) ! does not have any average value as boundary condition
else
do k = 1_pInt, grid3; do j = 1_pInt, grid(2); do i = 1_pInt, grid(1) do k = 1_pInt, grid3; do j = 1_pInt, grid(2); do i = 1_pInt, grid(1)
F_lambda33 = reshape(F_tau(1:9,i,j,k)-F(1:9,i,j,k),[3,3]) F_lambda33 = reshape(F_tau(1:9,i,j,k)-F(1:9,i,j,k),[3,3])
F_lambda33 = math_mul3333xx33(S_scale,math_mul33x33(F_lambda33, & F_lambda33 = math_mul3333xx33(S_scale,math_mul33x33(F_lambda33, &
math_mul3333xx33(C_scale,& math_mul3333xx33(C_scale,&
math_mul33x33(math_transpose33(F_lambda33),& math_mul33x33(math_transpose33(F_lambda33),&
F_lambda33) -math_I3))*0.5_pReal)& F_lambda33)-math_I3))*0.5_pReal)&
+ math_I3 + math_I3
F_tau(1:9,i,j,k) = reshape(F_lambda33,[9])+F(1:9,i,j,k) F_tau(1:9,i,j,k) = reshape(F_lambda33,[9])+F(1:9,i,j,k)
enddo; enddo; enddo enddo; enddo; enddo
endif endif
call DMDAVecRestoreArrayF90(da,solution_vec,xx_psc,ierr); CHKERRQ(ierr)
nullify(F)
nullify(F_tau)
call DMDAVecRestoreArrayF90(da,solution_vec,FandF_tau,ierr); CHKERRQ(ierr)
end subroutine Polarisation_forward end subroutine Polarisation_forward

238
src/spectral_utilities.f90 Normal file → Executable file
View File

@ -16,7 +16,7 @@ module spectral_utilities
#include <petsc/finclude/petscsys.h> #include <petsc/finclude/petscsys.h>
include 'fftw3-mpi.f03' include 'fftw3-mpi.f03'
logical, public :: cutBack =.false. !< cut back of BVP solver in case convergence is not achieved or a material point is terminally ill logical, public :: cutBack = .false. !< cut back of BVP solver in case convergence is not achieved or a material point is terminally ill
integer(pInt), public, parameter :: maxPhaseFields = 2_pInt integer(pInt), public, parameter :: maxPhaseFields = 2_pInt
integer(pInt), public :: nActiveFields = 0_pInt integer(pInt), public :: nActiveFields = 0_pInt
@ -145,8 +145,7 @@ module spectral_utilities
FIELD_UNDEFINED_ID, & FIELD_UNDEFINED_ID, &
FIELD_MECH_ID, & FIELD_MECH_ID, &
FIELD_THERMAL_ID, & FIELD_THERMAL_ID, &
FIELD_DAMAGE_ID, & FIELD_DAMAGE_ID
utilities_calcPlasticity
private :: & private :: &
utilities_getFreqDerivative utilities_getFreqDerivative
@ -154,9 +153,9 @@ contains
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief allocates all neccessary fields, sets debug flags, create plans for FFTW !> @brief allocates all neccessary fields, sets debug flags, create plans for FFTW
!> @details Sets the debug levels for general, divergence, restart and FFTW from the biwise coding !> @details Sets the debug levels for general, divergence, restart, and FFTW from the bitwise coding
!> provided by the debug module to logicals. !> provided by the debug module to logicals.
!> Allocates all fields used by FFTW and create the corresponding plans depending on the debug !> Allocate all fields used by FFTW and create the corresponding plans depending on the debug
!> level chosen. !> level chosen.
!> Initializes FFTW. !> Initializes FFTW.
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
@ -378,10 +377,10 @@ end subroutine utilities_init
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief updates references stiffness and potentially precalculated gamma operator !> @brief updates reference stiffness and potentially precalculated gamma operator
!> @details Sets the current reference stiffness to the stiffness given as an argument. !> @details Sets the current reference stiffness to the stiffness given as an argument.
!> If the gamma operator is precalculated, it is calculated with this stiffness. !> If the gamma operator is precalculated, it is calculated with this stiffness.
!> In case of a on-the-fly calculation, only the reference stiffness is updated. !> In case of an on-the-fly calculation, only the reference stiffness is updated.
!> Also writes out the current reference stiffness for restart. !> Also writes out the current reference stiffness for restart.
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine utilities_updateGamma(C,saveReference) subroutine utilities_updateGamma(C,saveReference)
@ -414,8 +413,7 @@ subroutine utilities_updateGamma(C,saveReference)
write(6,'(/,a)') ' writing reference stiffness to file' write(6,'(/,a)') ' writing reference stiffness to file'
flush(6) flush(6)
call IO_write_jobRealFile(777,'C_ref',size(C_ref)) call IO_write_jobRealFile(777,'C_ref',size(C_ref))
write (777,rec=1) C_ref write (777,rec=1) C_ref; close(777)
close(777)
endif endif
endif endif
@ -800,7 +798,7 @@ function utilities_maskedCompliance(rot_BC,mask_stress,C)
call math_invert(size_reduced, c_reduced, s_reduced, errmatinv) ! invert reduced stiffness call math_invert(size_reduced, c_reduced, s_reduced, errmatinv) ! invert reduced stiffness
if (any(IEEE_is_NaN(s_reduced))) errmatinv = .true. if (any(IEEE_is_NaN(s_reduced))) errmatinv = .true.
if(errmatinv) call IO_error(error_ID=400_pInt,ext_msg='utilities_maskedCompliance') if (errmatinv) call IO_error(error_ID=400_pInt,ext_msg='utilities_maskedCompliance')
temp99_Real = 0.0_pReal ! fill up compliance with zeros temp99_Real = 0.0_pReal ! fill up compliance with zeros
k = 0_pInt k = 0_pInt
do n = 1_pInt,9_pInt do n = 1_pInt,9_pInt
@ -818,28 +816,30 @@ function utilities_maskedCompliance(rot_BC,mask_stress,C)
sTimesC = matmul(c_reduced,s_reduced) sTimesC = matmul(c_reduced,s_reduced)
do m=1_pInt, size_reduced do m=1_pInt, size_reduced
do n=1_pInt, size_reduced do n=1_pInt, size_reduced
if(m==n .and. abs(sTimesC(m,n)) > (1.0_pReal + 10.0e-12_pReal)) errmatinv = .true. ! diagonal elements of S*C should be 1 errmatinv = errmatinv &
if(m/=n .and. abs(sTimesC(m,n)) > (0.0_pReal + 10.0e-12_pReal)) errmatinv = .true. ! off diagonal elements of S*C should be 0 .or. (m==n .and. abs(sTimesC(m,n)-1.0_pReal) > 1.0e-12_pReal) & ! diagonal elements of S*C should be 1
.or. (m/=n .and. abs(sTimesC(m,n)) > 1.0e-12_pReal) ! off-diagonal elements of S*C should be 0
enddo enddo
enddo enddo
if(debugGeneral .or. errmatinv) then if (debugGeneral .or. errmatinv) then
write(formatString, '(I16.16)') size_reduced write(formatString, '(i2)') size_reduced
formatString = '(/,a,/,'//trim(formatString)//'('//trim(formatString)//'(2x,es9.2,1x)/))' formatString = '(/,a,/,'//trim(formatString)//'('//trim(formatString)//'(2x,es9.2,1x)/))'
write(6,trim(formatString),advance='no') ' C * S (load) ', & write(6,trim(formatString),advance='no') ' C * S (load) ', &
transpose(matmul(c_reduced,s_reduced)) transpose(matmul(c_reduced,s_reduced))
write(6,trim(formatString),advance='no') ' S (load) ', transpose(s_reduced) write(6,trim(formatString),advance='no') ' S (load) ', transpose(s_reduced)
endif
if(errmatinv) call IO_error(error_ID=400_pInt,ext_msg='utilities_maskedCompliance') if(errmatinv) call IO_error(error_ID=400_pInt,ext_msg='utilities_maskedCompliance')
endif
deallocate(c_reduced) deallocate(c_reduced)
deallocate(s_reduced) deallocate(s_reduced)
deallocate(sTimesC) deallocate(sTimesC)
else else
temp99_real = 0.0_pReal temp99_real = 0.0_pReal
endif endif
if(debugGeneral) & if(debugGeneral) then
write(6,'(/,a,/,9(9(2x,f12.7,1x)/),/)',advance='no') ' Masked Compliance (load) * GPa =', & write(6,'(/,a,/,9(9(2x,f10.5,1x)/),/)',advance='no') &
transpose(temp99_Real*1.e9_pReal) ' Masked Compliance (load) / GPa =', transpose(temp99_Real*1.e-9_pReal)
flush(6) flush(6)
endif
utilities_maskedCompliance = math_Plain99to3333(temp99_Real) utilities_maskedCompliance = math_Plain99to3333(temp99_Real)
end function utilities_maskedCompliance end function utilities_maskedCompliance
@ -925,10 +925,10 @@ end subroutine utilities_fourierTensorDivergence
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief calculates constitutive response !> @brief calculate constitutive response from materialpoint_F0 to F during timeinc
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
subroutine utilities_constitutiveResponse(F_lastInc,F,timeinc, & subroutine utilities_constitutiveResponse(P,P_av,C_volAvg,C_minmaxAvg,&
P,C_volAvg,C_minmaxAvg,P_av,forwardData,rotation_BC) F,timeinc,rotation_BC)
use IO, only: & use IO, only: &
IO_error IO_error
use debug, only: & use debug, only: &
@ -941,30 +941,21 @@ subroutine utilities_constitutiveResponse(F_lastInc,F,timeinc, &
use mesh, only: & use mesh, only: &
grid,& grid,&
grid3 grid3
use FEsolving, only: &
restartWrite
use CPFEM2, only: &
CPFEM_general
use homogenization, only: & use homogenization, only: &
materialpoint_F0, &
materialpoint_F, & materialpoint_F, &
materialpoint_P, & materialpoint_P, &
materialpoint_dPdF materialpoint_dPdF, &
materialpoint_stressAndItsTangent
implicit none implicit none
real(pReal), intent(in), dimension(3,3,grid(1),grid(2),grid3) :: &
F_lastInc, & !< target deformation gradient
F !< previous deformation gradient
real(pReal), intent(in) :: timeinc !< loading time
logical, intent(in) :: forwardData !< age results
real(pReal), intent(in), dimension(3,3) :: rotation_BC !< rotation of load frame
real(pReal),intent(out), dimension(3,3,3,3) :: C_volAvg, C_minmaxAvg !< average stiffness real(pReal),intent(out), dimension(3,3,3,3) :: C_volAvg, C_minmaxAvg !< average stiffness
real(pReal),intent(out), dimension(3,3) :: P_av !< average PK stress real(pReal),intent(out), dimension(3,3) :: P_av !< average PK stress
real(pReal),intent(out), dimension(3,3,grid(1),grid(2),grid3) :: P !< PK stress real(pReal),intent(out), dimension(3,3,grid(1),grid(2),grid3) :: P !< PK stress
logical :: & real(pReal), intent(in), dimension(3,3,grid(1),grid(2),grid3) :: F !< deformation gradient target !< previous deformation gradient
age real(pReal), intent(in) :: timeinc !< loading time
real(pReal), intent(in), dimension(3,3) :: rotation_BC !< rotation of load frame
integer(pInt) :: & integer(pInt) :: &
j,k,ierr j,k,ierr
@ -976,16 +967,8 @@ subroutine utilities_constitutiveResponse(F_lastInc,F,timeinc, &
write(6,'(/,a)') ' ... evaluating constitutive response ......................................' write(6,'(/,a)') ' ... evaluating constitutive response ......................................'
flush(6) flush(6)
age = .False.
if (forwardData) then ! aging results materialpoint_F = reshape(F,[3,3,1,product(grid(1:2))*grid3]) ! set materialpoint target F to estimated field
age = .True.
materialpoint_F0 = reshape(F_lastInc, [3,3,1,product(grid(1:2))*grid3])
endif
if (cutBack) age = .False. ! restore saved variables
materialpoint_F = reshape(F,[3,3,1,product(grid(1:2))*grid3])
call debug_reset() ! this has no effect on rank >0
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
! calculate bounds of det(F) and report ! calculate bounds of det(F) and report
@ -1003,7 +986,19 @@ subroutine utilities_constitutiveResponse(F_lastInc,F,timeinc, &
flush(6) flush(6)
endif endif
call CPFEM_general(age,timeinc) call debug_reset() ! this has no effect on rank >0
call materialpoint_stressAndItsTangent(.true.,timeinc) ! calculate P field
P = reshape(materialpoint_P, [3,3,grid(1),grid(2),grid3])
P_av = sum(sum(sum(P,dim=5),dim=4),dim=3) * wgt ! average of P
call MPI_Allreduce(MPI_IN_PLACE,P_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
if (debugRotation) &
write(6,'(/,a,/,3(3(2x,f12.4,1x)/))',advance='no') ' Piola--Kirchhoff stress (lab) / MPa =',&
math_transpose33(P_av)*1.e-6_pReal
P_av = math_rotate_forward33(P_av,rotation_BC)
write(6,'(/,a,/,3(3(2x,f12.4,1x)/))',advance='no') ' Piola--Kirchhoff stress / MPa =',&
math_transpose33(P_av)*1.e-6_pReal
flush(6)
max_dPdF = 0.0_pReal max_dPdF = 0.0_pReal
max_dPdF_norm = 0.0_pReal max_dPdF_norm = 0.0_pReal
@ -1021,157 +1016,24 @@ subroutine utilities_constitutiveResponse(F_lastInc,F,timeinc, &
end do end do
call MPI_Allreduce(MPI_IN_PLACE,max_dPdF,81,MPI_DOUBLE,MPI_MAX,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,max_dPdF,81,MPI_DOUBLE,MPI_MAX,PETSC_COMM_WORLD,ierr)
if(ierr /=0_pInt) call IO_error(894_pInt, ext_msg='MPI_Allreduce max') if (ierr /= 0_pInt) call IO_error(894_pInt, ext_msg='MPI_Allreduce max')
call MPI_Allreduce(MPI_IN_PLACE,min_dPdF,81,MPI_DOUBLE,MPI_MIN,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,min_dPdF,81,MPI_DOUBLE,MPI_MIN,PETSC_COMM_WORLD,ierr)
if(ierr /=0_pInt) call IO_error(894_pInt, ext_msg='MPI_Allreduce min') if (ierr /= 0_pInt) call IO_error(894_pInt, ext_msg='MPI_Allreduce min')
C_minmaxAvg = 0.5_pReal*(max_dPdF + min_dPdF) C_minmaxAvg = 0.5_pReal*(max_dPdF + min_dPdF)
C_volAvg = sum(sum(materialpoint_dPdF,dim=6),dim=5) * wgt
C_volAvg = sum(sum(materialpoint_dPdF,dim=6),dim=5) * wgt
call MPI_Allreduce(MPI_IN_PLACE,C_volAvg,81,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr) call MPI_Allreduce(MPI_IN_PLACE,C_volAvg,81,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
call debug_info() ! this has no effect on rank >0 call debug_info() ! this has no effect on rank >0
restartWrite = .false. ! reset restartWrite status
cutBack = .false. ! reset cutBack status
P = reshape(materialpoint_P, [3,3,grid(1),grid(2),grid3])
P_av = sum(sum(sum(P,dim=5),dim=4),dim=3) * wgt ! average of P
call MPI_Allreduce(MPI_IN_PLACE,P_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
if (debugRotation) &
write(6,'(/,a,/,3(3(2x,f12.4,1x)/))',advance='no') ' Piola--Kirchhoff stress (lab) / MPa =',&
math_transpose33(P_av)*1.e-6_pReal
P_av = math_rotate_forward33(P_av,rotation_BC)
write(6,'(/,a,/,3(3(2x,f12.4,1x)/))',advance='no') ' Piola--Kirchhoff stress / MPa =',&
math_transpose33(P_av)*1.e-6_pReal
flush(6)
end subroutine utilities_constitutiveResponse end subroutine utilities_constitutiveResponse
!--------------------------------------------------------------------------------------------------
!> @brief calculates yield stress, plastic strain, total strain and their equivalent values
!--------------------------------------------------------------------------------------------------
subroutine utilities_calcPlasticity(yieldStress, plasticStrain, eqStress, eqTotalStrain, &
eqPlasticStrain, plasticWork, rotation_BC)
use crystallite, only: &
crystallite_Fe, &
crystallite_P, &
crystallite_subF
use material, only: &
homogenization_maxNgrains
use mesh, only: &
mesh_maxNips,&
mesh_NcpElems
use math, only: &
math_det33, &
math_inv33, &
math_mul33x33, &
math_trace33, &
math_transpose33, &
math_equivStrain33, &
math_equivStress33, &
math_rotate_forward33, &
math_identity2nd, &
math_crossproduct, &
math_eigenvectorBasisSym, &
math_eigenvectorBasisSym33, &
math_eigenvectorBasisSym33_log, &
math_eigenValuesVectorsSym33
implicit none
real(pReal), intent(inout) :: eqStress, eqPlasticStrain, plasticWork
real(pReal), intent(out) :: eqTotalStrain
real(pReal), dimension(3,3),intent(out) :: yieldStress, plasticStrain
real(pReal), intent(in), dimension(3,3) :: rotation_BC !< rotation of load frame
real(pReal), dimension(3,3) :: cauchy, P_av, F_av, Ve_av !< average
real(pReal), dimension(3) :: Values, S
real(pReal), dimension(3,3) :: Vectors, diag
real(pReal), dimension(3,3) :: &
Vp, F_temp, U, VT, R, V, V_total
real(pReal), dimension(3,3,homogenization_maxNgrains,mesh_maxNips,mesh_NcpElems) :: &
Be, Ve, Fe
real(pReal), dimension(15) :: WORK !< previous deformation gradient
integer(pInt) :: INFO, i, j, k, l, ierr
real(pReal) :: wgtm
real(pReal) :: eqStressOld, eqPlasticStrainOld, plasticWorkOld
external :: dgesvd
eqStressOld = eqStress
eqPlasticStrainOld = eqPlasticStrain
plasticWorkOld = plasticWork
wgtm = 1.0_pReal/real(mesh_NcpElems*mesh_maxNips*homogenization_maxNgrains,pReal)
diag = 0.0_pReal
P_av = sum(sum(sum(crystallite_P,dim=5),dim=4),dim=3) * wgtm
call MPI_Allreduce(MPI_IN_PLACE,P_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
P_av = math_rotate_forward33(P_av,rotation_BC)
F_av = sum(sum(sum(crystallite_subF,dim=5),dim=4),dim=3) * wgtm
call MPI_Allreduce(MPI_IN_PLACE,F_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
F_av = math_rotate_forward33(F_av,rotation_BC)
cauchy = 1.0_pReal/math_det33(F_av)*math_mul33x33(P_av,transpose(F_av))
yieldStress = cauchy
eqStress = math_equivStress33(cauchy)
F_temp = F_av
call dgesvd ('A', 'A', 3, 3, F_temp, 3, S, U, 3, VT, 3, WORK, 15, INFO) ! singular value decomposition
R = math_mul33x33(U, VT) ! rotation of polar decomposition
V = math_mul33x33(F_av,math_inv33(R))
call math_eigenValuesVectorsSym33(V,Values,Vectors)
do l = 1_pInt, 3_pInt
if (Values(l) < 0.0_pReal) then
Values(l) = -Values(l)
Vectors(1:3, l) = -Vectors(1:3, l)
endif
Values(l) = log(Values(l))
diag(l,l) = Values(l)
enddo
if (dot_product(Vectors(1:3,1),Vectors(1:3,2)) /= 0) then
Vectors(1:3,2) = math_crossproduct(Vectors(1:3,3), Vectors(1:3,1))
Vectors(1:3,2) = Vectors(1:3,2)/sqrt(dot_product(Vectors(1:3,2),Vectors(1:3,2)))
endif
if (dot_product(Vectors(1:3,2),Vectors(1:3,3)) /= 0) then
Vectors(1:3,3) = math_crossproduct(Vectors(1:3,1), Vectors(1:3,2))
Vectors(1:3,3) = Vectors(1:3,3)/sqrt(dot_product(Vectors(1:3,3),Vectors(1:3,3)))
endif
if (dot_product(Vectors(1:3,3),Vectors(1:3,1)) /= 0) then
Vectors(1:3,1) = math_crossproduct(Vectors(1:3,2), Vectors(1:3,3))
Vectors(1:3,1) = Vectors(1:3,1)/sqrt(dot_product(Vectors(1:3,1),Vectors(1:3,1)))
endif
V_total = REAL(math_mul33x33(Vectors, math_mul33x33(diag, transpose(Vectors))))
eqTotalStrain = math_equivStrain33(V_total)
do k = 1_pInt, mesh_NcpElems; do j = 1_pInt, mesh_maxNips; do i = 1_pInt,homogenization_maxNgrains
Fe(1:3,1:3,i,j,k) = crystallite_Fe(1:3,1:3,i,j,k)
Fe(1:3,1:3,i,j,k) = math_rotate_forward33(Fe(1:3,1:3,i,j,k),rotation_BC)
Be(1:3,1:3,i,j,k) = math_mul33x33(Fe(1:3,1:3,i,j,k),math_transpose33(Fe(1:3,1:3,i,j,k))) ! elastic part of left CauchyGreen deformation tensor
Ve(1:3,1:3,i,j,k) = math_eigenvectorBasisSym33_log(Be(1:3,1:3,i,j,k))
enddo; enddo; enddo
Ve_av = sum(sum(sum(Ve,dim=5),dim=4),dim=3) * wgtm
call MPI_Allreduce(MPI_IN_PLACE,Ve_av,9,MPI_DOUBLE,MPI_SUM,PETSC_COMM_WORLD,ierr)
Vp = V_total - Ve_av
eqPlasticStrain = math_equivStrain33(Vp)
plasticStrain = Vp
plasticWork = plasticWorkOld + 0.5*(eqStressOld + eqStress) * (eqPlasticStrain - eqPlasticStrainOld)
end subroutine utilities_calcPlasticity
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
!> @brief calculates forward rate, either guessing or just add delta/timeinc !> @brief calculates forward rate, either guessing or just add delta/timeinc
!-------------------------------------------------------------------------------------------------- !--------------------------------------------------------------------------------------------------
pure function utilities_calculateRate(avRate,timeinc_old,guess,field_lastInc,field) pure function utilities_calculateRate(heterogeneous,field0,field,dt,avRate)
use mesh, only: & use mesh, only: &
grid3, & grid3, &
grid grid
@ -1179,17 +1041,17 @@ pure function utilities_calculateRate(avRate,timeinc_old,guess,field_lastInc,fie
implicit none implicit none
real(pReal), intent(in), dimension(3,3) :: avRate !< homogeneous addon real(pReal), intent(in), dimension(3,3) :: avRate !< homogeneous addon
real(pReal), intent(in) :: & real(pReal), intent(in) :: &
timeinc_old !< timeinc of last step dt !< timeinc between field0 and field
logical, intent(in) :: & logical, intent(in) :: &
guess !< guess along former trajectory heterogeneous !< calculate field of rates
real(pReal), intent(in), dimension(3,3,grid(1),grid(2),grid3) :: & real(pReal), intent(in), dimension(3,3,grid(1),grid(2),grid3) :: &
field_lastInc, & !< data of previous step field0, & !< data of previous step
field !< data of current step field !< data of current step
real(pReal), dimension(3,3,grid(1),grid(2),grid3) :: & real(pReal), dimension(3,3,grid(1),grid(2),grid3) :: &
utilities_calculateRate utilities_calculateRate
if (guess) then if (heterogeneous) then
utilities_calculateRate = (field-field_lastInc) / timeinc_old utilities_calculateRate = (field-field0) / dt
else else
utilities_calculateRate = spread(spread(spread(avRate,3,grid(1)),4,grid(2)),5,grid3) utilities_calculateRate = spread(spread(spread(avRate,3,grid(1)),4,grid(2)),5,grid3)
endif endif