Report Typos and Errors    
Semi-Lagrangian Library
Modular library for kinetic and gyrokinetic simulations of plasmas in fusion energy devices.
sll_m_advection_1d_CSL.F90
Go to the documentation of this file.
1 !**************************************************************
2 ! Copyright INRIA
3 ! Authors :
4 ! CALVI project team
5 !
6 ! This code SeLaLib (for Semi-Lagrangian-Library)
7 ! is a parallel library for simulating the plasma turbulence
8 ! in a tokamak.
9 !
10 ! This software is governed by the CeCILL-B license
11 ! under French law and abiding by the rules of distribution
12 ! of free software. You can use, modify and redistribute
13 ! the software under the terms of the CeCILL-B license as
14 ! circulated by CEA, CNRS and INRIA at the following URL
15 ! "http://www.cecill.info".
16 !**************************************************************
17 
18 ! in development; should be at least cubic splines
19 ! attached with computation of characteristics
20 
24 !+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
25 #include "sll_memory.h"
26 #include "sll_working_precision.h"
27 
28  use sll_m_advection_1d_base, only: &
30 
32  sll_p_periodic, &
33  sll_p_set_to_limit, &
34  sll_p_user_defined
35 
41 
42  use sll_m_interpolators_1d_base, only: &
44 
45  implicit none
46 
47  public :: &
49 
50  private
51 !+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
52 
54 
55  class(sll_c_interpolator_1d), pointer :: interp
56  class(sll_c_characteristics_1d_base), pointer :: charac
57  sll_real64, dimension(:), pointer :: eta_coords
58  sll_real64, dimension(:), pointer :: eta_coords_unit
59  sll_real64, dimension(:), pointer :: eta_coords_unit_back
60  sll_real64, dimension(:), pointer :: charac_feet
61  sll_real64, dimension(:), pointer :: charac_feet_i
62  sll_real64, dimension(:), pointer :: buf1d
63  sll_real64, dimension(:), pointer :: buf1d_out
64  sll_int32 :: npts
65  sll_int32 :: bc_type
66  procedure(sll_i_signature_process_outside_point_1d), pointer, nopass :: &
67  process_outside_point
68 
69  contains
70  procedure, pass(adv) :: initialize => &
72  procedure, pass(adv) :: advect_1d => &
74  procedure, pass(adv) :: advect_1d_constant => &
76  procedure, pass(adv) :: delete => delete_csl_1d_advector
77  end type csl_1d_advector
78 
79 contains
81  interp, &
82  charac, &
83  Npts, &
84  eta_min, &
85  eta_max, &
86  eta_coords, &
87  bc_type, &
88  process_outside_point) &
89  result(adv)
90  type(csl_1d_advector), pointer :: adv
91  class(sll_c_interpolator_1d), pointer :: interp
92  class(sll_c_characteristics_1d_base), pointer :: charac
93  sll_int32, intent(in) :: npts
94  sll_real64, intent(in), optional :: eta_min
95  sll_real64, intent(in), optional :: eta_max
96  sll_real64, dimension(:), pointer, optional :: eta_coords
97  sll_int32, intent(in), optional :: bc_type
98  procedure(sll_i_signature_process_outside_point_1d), optional :: &
99  process_outside_point
100  sll_int32 :: ierr
101 
102  sll_allocate(adv, ierr)
103 
105  adv, &
106  interp, &
107  charac, &
108  npts, &
109  eta_min, &
110  eta_max, &
111  eta_coords, &
112  bc_type, &
113  process_outside_point)
114 
115  end function sll_f_new_csl_1d_advector
116 
118  adv, &
119  interp, &
120  charac, &
121  Npts, &
122  eta_min, &
123  eta_max, &
124  eta_coords, &
125  bc_type, &
126  process_outside_point)
127  class(csl_1d_advector), intent(inout) :: adv
128  class(sll_c_interpolator_1d), pointer :: interp
129  class(sll_c_characteristics_1d_base), pointer :: charac
130  sll_int32, intent(in) :: npts
131  sll_real64, intent(in), optional :: eta_min
132  sll_real64, intent(in), optional :: eta_max
133  sll_real64, dimension(:), pointer, optional :: eta_coords
134  sll_int32, intent(in), optional :: bc_type
135  procedure(sll_i_signature_process_outside_point_1d), optional :: &
136  process_outside_point
137  sll_int32 :: ierr
138  sll_int32 :: i
139  sll_real64 :: delta_eta
140 
141  adv%Npts = npts
142  adv%interp => interp
143  adv%charac => charac
144  sll_allocate(adv%eta_coords(npts), ierr)
145  sll_allocate(adv%eta_coords_unit(npts), ierr)
146  sll_allocate(adv%eta_coords_unit_back(npts), ierr)
147  sll_allocate(adv%buf1d(npts), ierr)
148  sll_allocate(adv%buf1d_out(npts), ierr)
149 
150  sll_allocate(adv%charac_feet(npts), ierr)
151  sll_allocate(adv%charac_feet_i(npts), ierr)
152 
153  if (present(eta_min) .and. present(eta_max)) then
154  if (present(eta_coords)) then
155  print *, '#provide either eta_coords or eta_min and eta_max'
156  print *, '#and not both in subroutine initialize_BSL_1d_advector'
157  stop
158  else
159  delta_eta = (eta_max - eta_min)/real(npts - 1, f64)
160  do i = 1, npts
161  adv%eta_coords(i) = eta_min + real(i - 1, f64)*delta_eta
162  end do
163  end if
164  else if (present(eta_coords)) then
165  if (size(eta_coords) < npts) then
166  print *, '#bad size for eta_coords in initialize_BSL_1d_advector'
167  stop
168  else
169  adv%eta_coords(1:npts) = eta_coords(1:npts)
170  end if
171  else
172  print *, '#Warning, we assume eta_min = 0._f64 eta_max = 1._f64'
173  delta_eta = 1._f64/real(npts - 1, f64)
174  do i = 1, npts
175  adv%eta_coords(i) = real(i - 1, f64)*delta_eta
176  end do
177  end if
178 
179  if (present(process_outside_point)) then
180  adv%process_outside_point => process_outside_point
181  adv%bc_type = sll_p_user_defined
182  else if (.not. (present(bc_type))) then
183  print *, '#provide boundary condition'
184  print *, '#bc_type or process_outside_point function'
185  print *, '#in initialize_CSL_1d_advector'
186  stop
187  else
188  adv%bc_type = bc_type
189  select case (bc_type)
190  case (sll_p_periodic)
191  adv%process_outside_point => sll_f_process_outside_point_periodic
192  case (sll_p_set_to_limit)
193  adv%process_outside_point => sll_f_process_outside_point_set_to_limit
194  case default
195  print *, '#bad value of boundary condition'
196  print *, '#in initialize_CSL_1d_advector'
197  stop
198  end select
199  end if
200 
201  if ((present(process_outside_point)) .and. (present(bc_type))) then
202  print *, '#provide either process_outside_point or bc_type'
203  print *, '#and not both'
204  print *, '#in initialize_CSL_1d_advector'
205  stop
206  end if
207 
208  adv%eta_coords_unit(1:npts) = &
209  (adv%eta_coords(1:npts) - adv%eta_coords(1)) &
210  /(adv%eta_coords(npts) - adv%eta_coords(1))
211 
212  end subroutine initialize_csl_1d_advector
213 
214  subroutine csl_advect_1d( &
215  adv, &
216  A, &
217  dt, &
218  input, &
219  output)
220  class(csl_1d_advector) :: adv
221  sll_real64, dimension(:), intent(in) :: a
222  sll_real64, intent(in) :: dt
223  sll_real64, dimension(:), intent(in) :: input
224  sll_real64, dimension(:), intent(out) :: output
225  sll_int32 :: npts
226  sll_real64 :: mean
227  sll_int32 :: i
228  sll_real64 :: eta_min
229  sll_real64 :: eta_max
230 
231  npts = adv%Npts
232 
233  eta_min = adv%eta_coords(1)
234  eta_max = adv%eta_coords(npts)
235 
236  call adv%charac%compute_characteristics( &
237  a, &
238  dt, &
239  adv%eta_coords, &
240  adv%charac_feet)
241 
242  !print *,'#eta_min=',eta_min,eta_max
243  !do i=1,Npts
244  ! print *,i,adv%charac_feet(i)
245  !enddo
246  !stop
247  do i = 1, npts
248  if ((adv%charac_feet(i) <= eta_min) .or. (adv%charac_feet(i) >= eta_max)) then
249  adv%charac_feet_i(i) = &
250  adv%process_outside_point(adv%charac_feet(i), eta_min, eta_max)
251  else
252  adv%charac_feet_i(i) = adv%charac_feet(i)
253  end if
254  end do
255 
256  adv%buf1d(1:npts - 1) = input(1:npts - 1)
257 
258 ! do i=1,Npts
259 ! !x1 = adv%eta_coords(1)+real(i-1,f64)*(adv%eta_coords(Npts)-adv%eta_coords(1))/real(Npts-1,f64)
260 ! x1 = adv%eta_coords_unit(i)
261 ! adv%buf1d(i) = cos(2._f64*sll_p_pi*x1)
262 ! enddo
263 
264  call function_to_primitive_csl(adv%buf1d, adv%eta_coords_unit, npts - 1, mean)
265 
266  !adv%buf1d(1:Npts) = adv%buf1d(1:Npts)*(adv%eta_coords(Npts)-adv%eta_coords(1))
267 
268  print *, mean
269  if (mean < 0.95) then
270  print *, '#mean value=', mean
271  !print *,'#charac=',adv%charac_feet(Npts)-adv%charac_feet(1)
272  !do i=1,Npts-1
273  ! print *,i,(adv%charac_feet(i+1)-adv%charac_feet(i))
274  !enddo
275 
276  stop
277  end if
278  !print *,'#mean=',mean
279 !
280 ! do i=1,Npts
281 ! !print *,i,input(i),adv%buf1d(i),adv%eta_coords_unit(i),adv%eta_coords(i)
282 ! print *,adv%eta_coords_unit(i),cos(2._f64*sll_p_pi*adv%eta_coords_unit(i)),adv%buf1d(i), &
283 ! sin(2._f64*sll_p_pi*adv%eta_coords_unit(i))/(2._f64*sll_p_pi)
284 ! !-sin(adv%eta_coords(i)-adv%eta_coords(1))/(2._f64*sll_p_pi)
285 ! enddo
286 
287  !do i=1,Npts
288  ! print *,i,adv%eta_coords(i),adv%charac_feet(i)
289  !enddo
290 
291 ! stop
292 
293 ! call adv%interp%compute_interpolants( &
294 ! input, &
295 ! adv%eta1_coords, &
296 ! adv%Npts1, &
297 ! adv%eta2_coords, &
298 ! adv%Npts2 )
299 
300  call adv%interp%interpolate_array( &
301  npts, &
302  adv%buf1d, &
303  adv%charac_feet_i, &
304  adv%buf1d_out)
305 
306  !adv%buf1d_out(1:Npts) = adv%buf1d_out(1:Npts)/(adv%eta_coords(Npts)-adv%eta_coords(1))
307 
308  adv%eta_coords_unit_back(1:npts) = &
309  (adv%charac_feet(1:npts) - adv%charac_feet(1)) &
310  /(adv%charac_feet(npts) - adv%charac_feet(1))
311 
313  adv%buf1d_out, &
314  adv%eta_coords_unit, &
315  !adv%eta_coords_unit, &
316  adv%eta_coords_unit_back, &
317  npts - 1, &
318  mean)
319 
320  output(1:npts - 1) = adv%buf1d_out(1:npts - 1)
321 
322  output(npts) = output(1) !warning only valid in periodic case
323 
324  end subroutine csl_advect_1d
325 
327  adv, &
328  A, &
329  dt, &
330  input, &
331  output)
332  class(csl_1d_advector) :: adv
333  sll_real64, intent(in) :: a
334  sll_real64, intent(in) :: dt
335  sll_real64, dimension(:), intent(in) :: input
336  sll_real64, dimension(:), intent(out) :: output
337  sll_real64, dimension(:), allocatable :: a1
338  sll_int32 :: ierr
339 
340  !this version is not optimized
341 
342  sll_allocate(a1(adv%Npts), ierr)
343 
344  a1 = a
345 
346  call adv%charac%compute_characteristics( &
347  a1, &
348  dt, &
349  adv%eta_coords, &
350  adv%charac_feet)
351 
352 ! call adv%interp%compute_interpolants( &
353 ! input, &
354 ! adv%eta1_coords, &
355 ! adv%Npts1, &
356 ! adv%eta2_coords, &
357 ! adv%Npts2 )
358 
359  call adv%interp%interpolate_array( &
360  adv%Npts, &
361  input, &
362  adv%charac_feet, &
363  output)
364 
365  sll_deallocate_array(a1, ierr)
366 
367  end subroutine csl_advect_1d_constant
368 
369  subroutine function_to_primitive_csl(f, node_positions, N, M)
370  sll_real64, dimension(:), intent(inout) :: f
371  sll_real64, dimension(:), intent(in) :: node_positions
372  sll_int32, intent(in):: n
373  sll_real64, intent(out)::m
374  sll_int32::i
375  sll_real64::tmp, tmp2
376 
377  !from f compute the mean
378  m = 0._f64
379  do i = 1, n
380  m = m + f(i)*(node_positions(i + 1) - node_positions(i))
381  end do
382 
383  f(1) = (f(1) - m)*(node_positions(2) - node_positions(1))
384  tmp = f(1)
385  f(1) = 0._f64
386  do i = 2, n!+1
387  f(i) = (f(i) - m)*(node_positions(i + 1) - node_positions(i))
388  tmp2 = f(i)
389  f(i) = f(i - 1) + tmp
390  tmp = tmp2
391  end do
392  f(n + 1) = f(n) + tmp
393 
394  !print *,M,f(1),f(N+1)
395 
396  end subroutine function_to_primitive_csl
397 
399  f, &
400  node_positions, &
401  node_positions_back, &
402  N, &
403  M)
404  sll_real64, dimension(:), intent(inout) :: f
405  sll_real64, dimension(:), intent(in) :: node_positions
406  sll_real64, dimension(:), intent(in) :: node_positions_back
407  sll_int32, intent(in):: n
408  sll_real64, intent(in)::m
409  sll_int32::i
410  sll_real64::tmp!,tmp2
411 
412  tmp = f(1)
413  do i = 1, n - 1
414  f(i) = f(i + 1) - f(i) + m*(node_positions_back(i + 1) - node_positions_back(i))
415  end do
416  f(n) = tmp - f(n) + m*(node_positions_back(n + 1) - node_positions_back(n))
417 
418  !from mean compute f
419  do i = 1, n
420  f(i) = f(i)/(node_positions(i + 1) - node_positions(i))
421  end do
422  !f(N+1) = f(1)
423  end subroutine primitive_to_function_csl
424 
425  subroutine delete_csl_1d_advector(adv)
426  class(csl_1d_advector), intent(inout) :: adv
427  sll_int32 :: ierr
428  sll_deallocate(adv%eta_coords, ierr)
429  sll_deallocate(adv%eta_coords_unit, ierr)
430  sll_deallocate(adv%eta_coords_unit_back, ierr)
431  sll_deallocate(adv%charac_feet, ierr)
432  sll_deallocate(adv%charac_feet_i, ierr)
433  sll_deallocate(adv%buf1d, ierr)
434  sll_deallocate(adv%buf1d_out, ierr)
435  end subroutine delete_csl_1d_advector
436 
437 end module sll_m_advection_1d_csl
Abstract class for advection.
conservative semi-lagrangian 1d advection
type(csl_1d_advector) function, pointer, public sll_f_new_csl_1d_advector(interp, charac, Npts, eta_min, eta_max, eta_coords, bc_type, process_outside_point)
subroutine primitive_to_function_csl(f, node_positions, node_positions_back, N, M)
subroutine csl_advect_1d_constant(adv, A, dt, input, output)
subroutine function_to_primitive_csl(f, node_positions, N, M)
subroutine initialize_csl_1d_advector(adv, interp, charac, Npts, eta_min, eta_max, eta_coords, bc_type, process_outside_point)
subroutine csl_advect_1d(adv, A, dt, input, output)
Abstract class for characteristic derived type.
function, public sll_f_process_outside_point_set_to_limit(eta, eta_min, eta_max)
function, public sll_f_process_outside_point_periodic(eta, eta_min, eta_max)
Module for 1D interpolation and reconstruction.
Abstract class for 1D interpolation and reconstruction.
    Report Typos and Errors