Neko 1.99.5
A portable framework for high-order spectral element flow simulations
Loading...
Searching...
No Matches
htable.f90
Go to the documentation of this file.
1! Copyright (c) 2019-2026, The Neko Authors
2! All rights reserved.
3!
4! Redistribution and use in source and binary forms, with or without
5! modification, are permitted provided that the following conditions
6! are met:
7!
8! * Redistributions of source code must retain the above copyright
9! notice, this list of conditions and the following disclaimer.
10!
11! * Redistributions in binary form must reproduce the above
12! copyright notice, this list of conditions and the following
13! disclaimer in the documentation and/or other materials provided
14! with the distribution.
15!
16! * Neither the name of the authors nor the names of its
17! contributors may be used to endorse or promote products derived
18! from this software without specific prior written permission.
19!
20! THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21! "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22! LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23! FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
24! COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25! INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26! BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
27! LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
28! CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
29! LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
30! ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
31! POSSIBILITY OF SUCH DAMAGE.
32!
52module htable
53 use num_types, only: dp, i4, i8
54 use utils, only: neko_error
55 use point, only : point_t
57 use math, only : neko_m_ln2
58 use, intrinsic :: iso_c_binding, only : c_ptr, c_associated
59 implicit none
60 private
61
63 type :: h_tuple_t
64 logical :: valid = .false.
65 logical :: skip = .false.
66 class(*), allocatable :: key
67 class(*), allocatable :: data
68 type(h_tuple_t), pointer :: next => null()
69 type(h_tuple_t), pointer :: prev => null()
70 end type h_tuple_t
71
73 type, public, abstract :: htable_t
74 integer, private :: size = 0
75 integer, private :: entries = 0
76 type(h_tuple_t), private, allocatable :: t(:)
77 type(h_tuple_t), pointer :: head => null()
78 type(h_tuple_t), pointer :: tail => null()
79 contains
80 procedure(htable_hash), pass(this), deferred :: hash
81 procedure, public, pass(this) :: clear => htable_clear
82 procedure, public, pass(this) :: free => htable_free
83 procedure, public, pass(this) :: num_entries => htable_num_entries
84 procedure, public, pass(this) :: get_size => htable_size
85 end type htable_t
86
87 abstract interface
88 pure function htable_hash(this, k, c) result(hash)
89 import htable_t
90 class(htable_t), intent(in) :: this
91 class(*), intent(in) :: k
92 integer, value :: c
93 integer :: hash
94 end function htable_hash
95 end interface
96
97 !
98 ! Implementations
99 !
100
102 type, public, extends(htable_t) :: htable_i4_t
103 contains
104 procedure, pass(this) :: init => htable_i4_init
105 procedure, pass(this) :: set => htable_i4_set
106 procedure, pass(this) :: get => htable_i4_get
107 procedure, pass(this) :: hash => htable_i4_hash
108 procedure, pass(this) :: remove => htable_i4_remove
109 end type htable_i4_t
110
112 type, public, extends(htable_t) :: htable_i8_t
113 contains
114 procedure, pass(this) :: init => htable_i8_init
115 procedure, pass(this) :: set => htable_i8_set
116 procedure, pass(this) :: get => htable_i8_get
117 procedure, pass(this) :: hash => htable_i8_hash
118 procedure, pass(this) :: remove => htable_i8_remove
119 end type htable_i8_t
120
122 type, public, extends(htable_t) :: htable_r8_t
123 contains
124 procedure, pass(this) :: init => htable_r8_init
125 procedure, pass(this) :: set => htable_r8_set
126 procedure, pass(this) :: get => htable_r8_get
127 procedure, pass(this) :: hash => htable_r8_hash
128 procedure, pass(this) :: remove => htable_r8_remove
129 end type htable_r8_t
130
132 type, public, extends(htable_t) :: htable_pt_t
133 contains
134 procedure, pass(this) :: init => htable_pt_init
135 procedure, pass(this) :: set => htable_pt_set
136 procedure, pass(this) :: get => htable_pt_get
137 procedure, pass(this) :: hash => htable_pt_hash
138 procedure, pass(this) :: remove => htable_pt_remove
139 end type htable_pt_t
140
142 type, public, extends(htable_t) :: htable_i4t2_t
143 contains
144 procedure, pass(this) :: init => htable_i4t2_init
145 procedure, pass(this) :: set => htable_i4t2_set
146 procedure, pass(this) :: get => htable_i4t2_get
147 procedure, pass(this) :: hash => htable_i4t2_hash
148 procedure, pass(this) :: remove => htable_i4t2_remove
149 end type htable_i4t2_t
150
152 type, public, extends(htable_t) :: htable_i4t4_t
153 contains
154 procedure, pass(this) :: init => htable_i4t4_init
155 procedure, pass(this) :: set => htable_i4t4_set
156 procedure, pass(this) :: get => htable_i4t4_get
157 procedure, pass(this) :: hash => htable_i4t4_hash
158 procedure, pass(this) :: remove => htable_i4t4_remove
159 end type htable_i4t4_t
160
162 type, public, extends(htable_t) :: htable_cptr_t
163 contains
164 procedure, pass(this) :: init => htable_cptr_init
165 procedure, pass(this) :: set => htable_cptr_set
166 procedure, pass(this) :: get => htable_cptr_get
167 procedure, pass(this) :: hash => htable_cptr_hash
168 procedure, pass(this) :: remove => htable_cptr_remove
169 end type htable_cptr_t
170
171 !
172 ! Iterators
173 !
174
176 type, public, abstract :: htable_iter_t
177 class(htable_t), pointer :: t
178 type(h_tuple_t), pointer :: current => null()
179 contains
180 procedure, public, pass(this) :: next => htable_iter_next
181 procedure, public, pass(this) :: reset => htable_iter_reset
182 procedure, public, pass(this) :: data => htable_iter_data
183 end type htable_iter_t
184
186 type, public, extends(htable_iter_t) :: htable_iter_i4_t
187 contains
188 procedure, pass(this) :: init => htable_iter_i4_init
189 procedure, pass(this) :: value => htable_iter_i4_value
190 procedure, pass(this) :: key => htable_iter_i4_key
192 end type htable_iter_i4_t
193
195 type, public, extends(htable_iter_t) :: htable_iter_i8_t
196 contains
197 procedure, pass(this) :: init => htable_iter_i8_init
198 procedure, pass(this) :: value => htable_iter_i8_value
199 procedure, pass(this) :: key => htable_iter_i8_key
201 end type htable_iter_i8_t
202
204 type, public, extends(htable_iter_t) :: htable_iter_r8_t
205 contains
206 procedure, pass(this) :: init => htable_iter_r8_init
207 procedure, pass(this) :: value => htable_iter_r8_value
208 procedure, pass(this) :: key => htable_iter_r8_key
210 end type htable_iter_r8_t
211
213 type, public, extends(htable_iter_t) :: htable_iter_pt_t
214 contains
215 procedure, pass(this) :: init => htable_iter_pt_init
216 procedure, pass(this) :: value => htable_iter_pt_value
217 procedure, pass(this) :: key => htable_iter_pt_key
219 end type htable_iter_pt_t
220
222 type, public, extends(htable_iter_t) :: htable_iter_i4t2_t
223 contains
224 procedure, pass(this) :: init => htable_iter_i4t2_init
225 procedure, pass(this) :: value => htable_iter_i4t2_value
226 procedure, pass(this) :: key => htable_iter_i4t2_key
228 end type htable_iter_i4t2_t
229
231 type, public, extends(htable_iter_t) :: htable_iter_i4t4_t
232 contains
233 procedure, pass(this) :: init => htable_iter_i4t4_init
234 procedure, pass(this) :: value => htable_iter_i4t4_value
235 procedure, pass(this) :: key => htable_iter_i4t4_key
237 end type htable_iter_i4t4_t
238
240 type, public, extends(htable_iter_t) :: htable_iter_cptr_t
241 contains
242 procedure, pass(this) :: init => htable_iter_cptr_init
243 procedure, pass(this) :: value => htable_iter_cptr_value
244 procedure, pass(this) :: key => htable_iter_cptr_key
246 end type htable_iter_cptr_t
247
248 !
249 ! Type wrappers
250 !
251 type, public :: h_cptr_t
252 type(c_ptr) :: ptr
253 end type h_cptr_t
254
255contains
256
258 subroutine htable_init(this, size, key, data)
259 class(htable_t), intent(inout) :: this
260 integer, value :: size
261 class(*), target, intent(in) :: key
262 class(*), target, intent(in), optional :: data
263 class(*), pointer :: data_ptr
264 integer :: i
265
266
267 call htable_free(this)
268
269 if (size .lt. 4) then
270 size = 4
271 end if
272
273 size = ishft(1, ceiling(log(dble(size)) / neko_m_ln2))
274
275 allocate(this%t(0:size))
276 this%t(:)%valid = .false.
277 this%size = size
278 this%entries = 0
279
280 data_ptr => key
281 if (present(data)) then
282 data_ptr => data
283 end if
284
285 do i = 0, size
286 allocate(this%t(i)%key, source=key)
287 allocate(this%t(i)%data, source=data_ptr)
288 end do
289 end subroutine htable_init
290
292 subroutine htable_free(this)
293 class(htable_t), intent(inout) :: this
294 integer :: i
295
296 nullify(this%head)
297 nullify(this%tail)
298
299 if (allocated(this%t)) then
300 do i = 0, this%size
301 deallocate(this%t(i)%key)
302 deallocate(this%t(i)%data)
303 end do
304 deallocate(this%t)
305 end if
306
307 this%size = 0
308 this%entries = 0
309
310 end subroutine htable_free
311
313 subroutine htable_clear(this)
314 class(htable_t), intent(inout) :: this
315
316 if (allocated(this%t)) then
317 this%t(:)%valid = .false.
318 this%entries = 0
319 else
320 call neko_error("Hash table not allocated")
321 end if
322
323 end subroutine htable_clear
324
326 pure function htable_num_entries(this) result(entries)
327 class(htable_t), intent(in) :: this
328 integer :: entries
329 entries = this%entries
330 end function htable_num_entries
331
333 pure function htable_size(this) result(size)
334 class(htable_t), intent(in) :: this
335 integer :: size
336 size = this%size
337 end function htable_size
338
339
341 recursive subroutine htable_set(this, key, data)
342 class(htable_t), target, intent(inout) :: this
343 class(*), intent(inout) :: key
344 class(*), intent(inout) :: data
345 class(htable_t), allocatable :: tmp
346 integer index, i, c
347
348 c = 0
349 i = log(1.0/this%size)/log(0.6)
350 index = 0
351
352 do while (i .ge. 0)
353 index = this%hash(key, c**2)
354 if (index .lt. 0) then
355 call neko_error("Invalid hash generated")
356 end if
358 if ((.not. this%t(index)%valid) .or. &
359 htable_eq_key(this, index, key)) then
360 call htable_set_key(this, index, key)
361 call htable_set_data(this, index, data)
362 if (.not. this%t(index)%valid) then
363 this%entries = this%entries + 1
364 if (associated(this%tail)) then
365 this%tail%next => this%t(index)
366 this%t(index)%prev => this%tail
367 this%tail => this%t(index)
368 else
369 this%head => this%t(index)
370 this%tail => this%t(index)
371 end if
372 end if
373 this%t(index)%valid = .true.
374 this%t(index)%skip = .false.
375 return
376 end if
377 i = i - 1
378 c = c + 1
379 end do
380
381 select type(key)
382 type is (integer)
383 allocate(htable_i4_t::tmp)
384 type is (integer(i8))
385 allocate(htable_i8_t::tmp)
386 type is (double precision)
387 allocate(htable_r8_t::tmp)
388 type is (point_t)
389 allocate(htable_pt_t::tmp)
390 type is (tuple_i4_t)
391 allocate(htable_i4t2_t::tmp)
392 type is (tuple4_i4_t)
393 allocate(htable_i4t4_t::tmp)
394 type is (h_cptr_t)
395 allocate(htable_cptr_t::tmp)
396 class default
397 call neko_error('Invalid htable key')
398 end select
399
400 call htable_init(tmp, ishft(this%size, 1), key, data)
401
402 !
403 ! When rebuilding the table we used the following loop:
404 !
405 ! do i = 0, this%size - 1
406 ! if (this%t(i)%valid) then
407 ! call htable_set(tmp, this%t(i)%key, this%t(i)%data)
408 ! end if
409 ! end do
410 !
411 ! However, CCE 18.x (and probably other llvm based compilers)
412 ! segfault faults unless the data variable is enclosed in a
413 ! select type block
414 !
415
416 do i = 0, this%size - 1
417 if (this%t(i)%valid) then
418 select type (datap => this%t(i)%data)
419 type is (integer)
420 call htable_set(tmp, this%t(i)%key, datap)
421 type is (integer(i8))
422 call htable_set(tmp, this%t(i)%key, datap)
423 type is (double precision)
424 call htable_set(tmp, this%t(i)%key, datap)
425 type is (point_t)
426 call htable_set(tmp, this%t(i)%key, datap)
427 class is (tuple_t)
428 select type(tuplep => datap)
429 type is (tuple_i4_t)
430 call htable_set(tmp, this%t(i)%key, tuplep)
431 type is (tuple4_i4_t)
432 call htable_set(tmp, this%t(i)%key, tuplep)
433 end select
434 type is (h_cptr_t)
435 call htable_set(tmp, this%t(i)%key, datap)
436 class default
437 call neko_error('Invalid htable data')
438 end select
439 end if
440 end do
441
442 this%head => tmp%head
443 this%tail => tmp%tail
444 this%size = tmp%size
445 call move_alloc(tmp%t, this%t)
446
447 call htable_set(this, key, data)
448
449 end subroutine htable_set
450
452 function htable_get(this, key, data) result(rcode)
453 class(htable_t), intent(inout) :: this
454 class(*), intent(inout) :: key
455 class(*), intent(inout) :: data
456 integer :: rcode
457 integer :: index, i, c
458
459 c = 0
460 i = log(1.0/this%size)/log(0.6)
461
462 do while (i .ge. 0)
463 index = this%hash(key, c**2)
464 if (index .lt. 0) then
465 call neko_error("Invalid hash generated")
466 end if
467
468 if (.not. this%t(index)%valid .and. &
469 .not. this%t(index)%skip) then
470 rcode = 1
471 return
472 else if ((this%t(index)%valid) .and. &
473 htable_eq_key(this, index, key)) then
474 call htable_get_data(this, index, data)
475 rcode = 0
476 return
477 end if
478 i = i - 1
479 c = c + 1
480 end do
481 rcode = 1
482 end function htable_get
483
485 subroutine htable_remove(this, key)
486 class(htable_t), intent(inout) :: this
487 class(*), intent(inout) :: key
488 integer :: index, i, c
489
490 c = 0
491 i = log(1.0/this%size)/log(0.6)
492
493 do while (i .ge. 0)
494 index = this%hash(key, c**2)
495 if (index .lt. 0) then
496 call neko_error("Invalid hash generated")
497 end if
498
499 if ((this%t(index)%valid) .and. &
500 htable_eq_key(this, index, key)) then
501
502 if (associated(this%t(index)%prev)) then
503 this%t(index)%prev%next => this%t(index)%next
504 else
505 this%head => this%t(index)%next
506 end if
507
508 if (associated(this%t(index)%next)) then
509 this%t(index)%next%prev => this%t(index)%prev
510 else
511 this%tail => this%t(index)%prev
512 end if
513
514 this%t(index)%valid = .false.
515 this%t(index)%skip = .true.
516 this%entries = this%entries - 1
517 return
518 end if
519 i = i - 1
520 c = c + 1
521 end do
522 end subroutine htable_remove
523
525 subroutine htable_set_data(this, idx, data)
526 class(htable_t), target, intent(inout) :: this
527 integer, intent(in) :: idx
528 class(*), intent(in) :: data
529 class(*), pointer :: hdp
530
531 hdp => this%t(idx)%data
532 select type (data)
533 type is (integer)
534 select type(hdp)
535 type is (integer)
536 hdp = data
537 end select
538 type is (integer(i8))
539 select type(hdp)
540 type is (integer(i8))
541 hdp = data
542 end select
543 type is (double precision)
544 select type(hdp)
545 type is (double precision)
546 hdp = data
547 end select
548 type is (point_t)
549 select type(hdp)
550 type is (point_t)
551 hdp = data
552 end select
553 class is (tuple_t)
554 select type(hdp)
555 type is (tuple_i4_t)
556 hdp = data
557 type is (tuple4_i4_t)
558 hdp = data
559 end select
560 type is (h_cptr_t)
561 select type(hdp)
562 type is (h_cptr_t)
563 hdp = data
564 end select
565 class default
566 call neko_error('Invalid htable data (set)')
567 end select
568 end subroutine htable_set_data
569
571 subroutine htable_get_data(this, idx, data)
572 class(htable_t), intent(in) :: this
573 integer, intent(in) :: idx
574 class(*), intent(inout) :: data
575
576 select type (hdp=>this%t(idx)%data)
577 type is (integer)
578 select type(data)
579 type is (integer)
580 data = hdp
581 end select
582 type is (integer(i8))
583 select type(data)
584 type is (integer(i8))
585 data = hdp
586 end select
587 type is (double precision)
588 select type(data)
589 type is (double precision)
590 data = hdp
591 end select
592 type is (point_t)
593 select type(data)
594 type is (point_t)
595 data = hdp
596 end select
597 class is (tuple_t)
598 select type(data)
599 type is (tuple_i4_t)
600 data = hdp
601 type is (tuple4_i4_t)
602 data = hdp
603 end select
604 type is (h_cptr_t)
605 select type (data)
606 type is (h_cptr_t)
607 data = hdp
608 end select
609 class default
610 call neko_error('Invalid htable data (get)')
611 end select
612 end subroutine htable_get_data
613
615 pure function htable_eq_key(this, idx, key) result(res)
616 class(htable_t), intent(in) :: this
617 integer, intent(in) :: idx
618 class(*), intent(in) :: key
619 logical :: res
620
621 res = .true.
622 select type (kp=>this%t(idx)%key)
623 type is (integer)
624 select type(key)
625 type is (integer)
626 res = (kp .eq. key)
627 end select
628 type is (integer(i8))
629 select type(key)
630 type is (integer(i8))
631 res = (kp .eq. key)
632 end select
633 type is (double precision)
634 select type(key)
635 type is (double precision)
636 res = abs(kp - key) .lt. epsilon(1.0_dp)
637 end select
638 type is (point_t)
639 select type (key)
640 type is (point_t)
641 res = (kp .eq. key)
642 end select
643 class is (tuple_t)
644 select type (key)
645 type is (tuple_i4_t)
646 res = (key .eq. kp)
647 type is (tuple4_i4_t)
648 res = (key .eq. kp)
649 end select
650 type is (h_cptr_t)
651 select type (key)
652 type is (h_cptr_t)
653 res = c_associated(kp%ptr, key%ptr)
654 end select
655 end select
656 end function htable_eq_key
657
659 subroutine htable_set_key(this, idx, key)
660 class(htable_t), target, intent(inout) :: this
661 integer, intent(in) :: idx
662 class(*), intent(in) :: key
663 class(*), pointer :: kp
664
665 kp => this%t(idx)%key
666 select type(key)
667 type is (integer)
668 select type(kp)
669 type is (integer)
670 kp = key
671 end select
672 type is (integer(i8))
673 select type(kp)
674 type is (integer(i8))
675 kp = key
676 end select
677 type is (double precision)
678 select type(kp)
679 type is (double precision)
680 kp = key
681 end select
682 type is (point_t)
683 select type (kp)
684 type is (point_t)
685 kp = key
686 end select
687 class is (tuple_t)
688 select type(kp)
689 type is (tuple_i4_t)
690 kp = key
691 type is (tuple4_i4_t)
692 kp = key
693 end select
694 type is (h_cptr_t)
695 select type(kp)
696 type is (h_cptr_t)
697 kp = key
698 end select
699 class default
700 call neko_error('Invalid htable key (set)')
701 end select
702 end subroutine htable_set_key
703
705 function htable_iter_next(this) result(valid)
706 class(htable_iter_t), target, intent(inout) :: this
707 logical :: valid
708
709 if (.not. associated(this%current)) then
710 this%current => this%t%head
711 valid = associated(this%current)
712 else if (associated(this%current)) then
713 if (associated(this%current, this%t%tail)) then
714 valid = .false.
715 else
716 this%current => this%current%next
717 valid = associated(this%current)
718 end if
719 end if
720
721 end function htable_iter_next
722
724 subroutine htable_iter_reset(this)
725 class(htable_iter_t), intent(inout) :: this
726 nullify(this%current)
727 end subroutine htable_iter_reset
728
733 subroutine htable_iter_data(this, data)
734 class(htable_iter_t), target, intent(inout) :: this
735 class(*), intent(inout) :: data
736 class(*), pointer :: hdp
737
738 hdp => this%current%data
739 select type(hdp)
740 type is (integer)
741 select type (data)
742 type is (integer)
743 data = hdp
744 end select
745 type is (integer(i8))
746 select type (data)
747 type is (integer(i8))
748 data = hdp
749 end select
750 type is (double precision)
751 select type(data)
752 type is (double precision)
753 data = hdp
754 end select
755 type is (point_t)
756 select type (data)
757 type is (point_t)
758 data = hdp
759 end select
760 class is (tuple_t)
761 select type (data)
762 type is (tuple_i4_t)
763 data = hdp
764 type is (tuple4_i4_t)
765 data = hdp
766 end select
767 type is (h_cptr_t)
768 select type (data)
769 type is (h_cptr_t)
770 data = hdp
771 end select
772 class default
773 call neko_error('Invalid htable data (iter)')
774 end select
775
776 end subroutine htable_iter_data
777
778 !
779 ! Integer based implementation
780 !
782 subroutine htable_i4_init(this, size, data)
783 class(htable_i4_t), intent(inout) :: this
784 integer, value :: size
785 class(*), intent(inout), optional :: data
786 integer :: key
787
788 if (present(data)) then
789 call htable_init(this, size, key, data)
790 else
791 call htable_init(this, size, key)
792 end if
793
794 end subroutine htable_i4_init
795
797 subroutine htable_i4_set(this, key, data)
798 class(htable_i4_t), intent(inout) :: this
799 integer, intent(inout) :: key
800 class(*), intent(inout) :: data
801
802 call htable_set(this, key, data)
803
804 end subroutine htable_i4_set
805
807 function htable_i4_get(this, key, data) result(rcode)
808 class(htable_i4_t), intent(inout) :: this
809 integer, intent(inout) :: key
810 class(*), intent(inout) :: data
811 integer :: rcode
812
813 rcode = htable_get(this, key, data)
814
815 end function htable_i4_get
816
818 pure function htable_i4_hash(this, k, c) result(hash)
819 class(htable_i4_t), intent(in) :: this
820 class(*), intent(in) :: k
821 integer, value :: c
822 integer :: hash
823 integer(kind=i8) :: tmp
824 integer(kind=i8), parameter :: m1 = int(z'7ed55d15', i8)
825 integer(kind=i8), parameter :: m2 = int(z'c761c23c', i8)
826 integer(kind=i8), parameter :: m3 = int(z'165667b1', i8)
827 integer(kind=i8), parameter :: m4 = int(z'd3a2646c', i8)
828 integer(kind=i8), parameter :: m5 = int(z'fd7046c5', i8)
829 integer(kind=i8), parameter :: m6 = int(z'b55a4f09', i8)
830
831 select type(k)
832 type is (integer)
833 tmp = int(k, i8)
834 tmp = (k + m1) + ishft(k, 12)
835 tmp = ieor(ieor(tmp, m2), ishft(tmp, -19))
836 tmp = (tmp + m3) + ishft(tmp, 5)
837 tmp = ieor((tmp + m4), ishft(tmp, 9))
838 tmp = (tmp + m5) + ishft(tmp, 3)
839 tmp = ieor(ieor(tmp, m6), ishft(tmp, -16))
840 tmp = modulo(tmp + int(c, i8), int(this%size, i8))
841 hash = int(tmp, i4)
842 class default
843 hash = -1
844 end select
845 end function htable_i4_hash
846
848 subroutine htable_i4_remove(this, key)
849 class(htable_i4_t), intent(inout) :: this
850 integer, intent(inout) :: key
851
852 call htable_remove(this, key)
853
854 end subroutine htable_i4_remove
855
857 subroutine htable_iter_i4_init(this, t)
858 class(htable_iter_i4_t), intent(inout) :: this
859 type(htable_i4_t), target, intent(inout) :: t
860
861 this%t => t
862
863 end subroutine htable_iter_i4_init
864
866 subroutine htable_iter_i4_free(this)
867 type(htable_iter_i4_t), intent(inout) :: this
868 nullify(this%t)
869 nullify(this%current)
870 end subroutine htable_iter_i4_free
871
873 function htable_iter_i4_value(this) result(value)
874 class(htable_iter_i4_t), target, intent(inout) :: this
875 integer, pointer :: value
876
877 select type (hdp => this%current%data)
878 type is (integer)
879 value => hdp
880 class default
881 call neko_error('Key and data of different kind (i4)')
882 end select
883
884 end function htable_iter_i4_value
885
887 function htable_iter_i4_key(this) result(key)
888 class(htable_iter_i4_t), target, intent(inout) :: this
889 integer, pointer :: key
890
891 select type (kp => this%current%key)
892 type is (integer)
893 key => kp
894 class default
895 call neko_error('Invalid key (i4)')
896 end select
897
898 end function htable_iter_i4_key
899
900 !
901 ! Integer*8 based implementation
902 !
904 subroutine htable_i8_init(this, size, data)
905 class(htable_i8_t), intent(inout) :: this
906 integer, value :: size
907 class(*), intent(inout), optional :: data
908 integer(kind=i8) :: key
909
910 if (present(data)) then
911 call htable_init(this, size, key, data)
912 else
913 call htable_init(this, size, key)
914 end if
915
916 end subroutine htable_i8_init
917
919 subroutine htable_i8_set(this, key, data)
920 class(htable_i8_t), intent(inout) :: this
921 integer(kind=i8), intent(inout) :: key
922 class(*), intent(inout) :: data
923
924 call htable_set(this, key, data)
925
926 end subroutine htable_i8_set
927
929 function htable_i8_get(this, key, data) result(rcode)
930 class(htable_i8_t), intent(inout) :: this
931 integer(kind=i8), intent(inout) :: key
932 class(*), intent(inout) :: data
933 integer :: rcode
934
935 rcode = htable_get(this, key, data)
936
937 end function htable_i8_get
938
940 pure function htable_i8_hash(this, k, c) result(hash)
941 class(htable_i8_t), intent(in) :: this
942 class(*), intent(in) :: k
943 integer, value :: c
944 integer :: hash
945 integer(kind=i8) :: tmp
946 integer(kind=i8), parameter :: m1 = int(z'7ed55d15', i8)
947 integer(kind=i8), parameter :: m2 = int(z'c761c23c', i8)
948 integer(kind=i8), parameter :: m3 = int(z'165667b1', i8)
949 integer(kind=i8), parameter :: m4 = int(z'd3a2646c', i8)
950 integer(kind=i8), parameter :: m5 = int(z'fd7046c5', i8)
951 integer(kind=i8), parameter :: m6 = int(z'b55a4f09', i8)
952
953 select type(k)
954 type is (integer(i8))
955 tmp = (k + m1) + ishft(k, 12)
956 tmp = ieor(ieor(tmp, m2), ishft(tmp, -19))
957 tmp = (tmp + m3) + ishft(tmp, 5)
958 tmp = ieor((tmp + m4), ishft(tmp, 9))
959 tmp = (tmp + m5) + ishft(tmp, 3)
960 tmp = ieor(ieor(tmp, m6), ishft(tmp, -16))
961 hash = int(modulo(tmp, int(this%size, i8)), i4)
963 hash = int(modulo((k * 2654435761_i8) + int(c, i8), &
964 int(this%size, i8)), i4)
965 class default
966 hash = -1
967 end select
968 end function htable_i8_hash
969
971 subroutine htable_i8_remove(this, key)
972 class(htable_i8_t), intent(inout) :: this
973 integer(kind=i8), intent(inout) :: key
974
975 call htable_remove(this, key)
976
977 end subroutine htable_i8_remove
978
980 subroutine htable_iter_i8_init(this, t)
981 class(htable_iter_i8_t), intent(inout) :: this
982 type(htable_i8_t), target, intent(inout) :: t
983
984 this%t => t
985
986 end subroutine htable_iter_i8_init
987
989 subroutine htable_iter_i8_free(this)
990 type(htable_iter_i8_t), intent(inout) :: this
991 nullify(this%t)
992 nullify(this%current)
993 end subroutine htable_iter_i8_free
994
996 function htable_iter_i8_value(this) result(value)
997 class(htable_iter_i8_t), target, intent(inout) :: this
998 integer(kind=i8), pointer :: value
999
1000 select type (hdp => this%current%data)
1001 type is (integer(i8))
1002 value => hdp
1003 class default
1004 call neko_error('Key and data of different kind (i8)')
1005 end select
1006
1007 end function htable_iter_i8_value
1008
1010 function htable_iter_i8_key(this) result(key)
1011 class(htable_iter_i8_t), target, intent(inout) :: this
1012 integer(kind=i8), pointer :: key
1013
1014 ! We should not need this extra select block, and it works great
1015 ! without it for GNU, Intel and NEC, but breaks horribly on Cray
1016 ! (>11.0.x) when using high opt. levels.
1017 select type(hti => this)
1018 type is(htable_iter_i8_t)
1019 select type (kp => hti%current%key)
1020 type is (integer(i8))
1021 key => kp
1022 class default
1023 call neko_error('Invalid key (i8)')
1024 end select
1025 class default
1026 call neko_error('Corrupt htable iter. (i8)')
1027 end select
1028
1029 end function htable_iter_i8_key
1030
1031
1032 !
1033 ! Double precision based implementation
1034 !
1036 subroutine htable_r8_init(this, size, data)
1037 class(htable_r8_t), intent(inout) :: this
1038 integer, value :: size
1039 class(*), intent(inout), optional :: data
1040 real(kind=dp) :: key
1041
1042 if (present(data)) then
1043 call htable_init(this, size, key, data)
1044 else
1045 call htable_init(this, size, key)
1046 end if
1047
1048 end subroutine htable_r8_init
1049
1051 subroutine htable_r8_set(this, key, data)
1052 class(htable_r8_t), intent(inout) :: this
1053 real(kind=dp), intent(inout) :: key
1054 class(*), intent(inout) :: data
1055
1056 call htable_set(this, key, data)
1057
1058 end subroutine htable_r8_set
1059
1061 function htable_r8_get(this, key, data) result(rcode)
1062 class(htable_r8_t), intent(inout) :: this
1063 real(kind=dp), intent(inout) :: key
1064 class(*), intent(inout) :: data
1065 integer :: rcode
1066
1067 rcode = htable_get(this, key, data)
1068
1069 end function htable_r8_get
1070
1072 pure function htable_r8_hash(this, k, c) result(hash)
1073 class(htable_r8_t), intent(in) :: this
1074 class(*), intent(in) :: k
1075 integer, value :: c
1076 integer :: hash
1077 select type(k)
1078 type is (double precision)
1079 hash = modulo(floor((2d0 * abs(fraction(k)) - 1d0) * 2**16) + c, &
1080 this%size)
1081 class default
1082 hash = -1
1083 end select
1084 end function htable_r8_hash
1085
1087 subroutine htable_r8_remove(this, key)
1088 class(htable_r8_t), intent(inout) :: this
1089 real(kind=dp), intent(inout) :: key
1090
1091 call htable_remove(this, key)
1092
1093 end subroutine htable_r8_remove
1094
1095
1097 subroutine htable_iter_r8_init(this, t)
1098 class(htable_iter_r8_t), intent(inout) :: this
1099 type(htable_r8_t), target, intent(inout) :: t
1100
1101 this%t => t
1102
1103 end subroutine htable_iter_r8_init
1104
1106 subroutine htable_iter_r8_free(this)
1107 type(htable_iter_r8_t), intent(inout) :: this
1108 nullify(this%t)
1109 nullify(this%current)
1110 end subroutine htable_iter_r8_free
1111
1113 function htable_iter_r8_value(this) result(value)
1114 class(htable_iter_r8_t), target, intent(inout) :: this
1115 real(kind=dp), pointer :: value
1116
1117 select type (hdp => this%current%data)
1118 type is (double precision)
1119 value => hdp
1120 class default
1121 call neko_error('Key and data of different kind (r8)')
1122 end select
1123
1124 end function htable_iter_r8_value
1125
1127 function htable_iter_r8_key(this) result(key)
1128 class(htable_iter_r8_t), target, intent(inout) :: this
1129 real(kind=dp), pointer :: key
1130
1131 select type (kp => this%current%key)
1132 type is (double precision)
1133 key => kp
1134 class default
1135 call neko_error('Invalid key (r8)')
1136 end select
1137
1138 end function htable_iter_r8_key
1139
1140 !
1141 ! Point based implementation
1142 !
1144 subroutine htable_pt_init(this, size, data)
1145 class(htable_pt_t), intent(inout) :: this
1146 integer, value :: size
1147 class(*), intent(inout), optional :: data
1148 type(point_t) :: key
1149
1150 if (present(data)) then
1151 call htable_init(this, size, key, data)
1152 else
1153 call htable_init(this, size, key)
1154 end if
1155
1156 end subroutine htable_pt_init
1157
1159 subroutine htable_pt_set(this, key, data)
1160 class(htable_pt_t), intent(inout) :: this
1161 type(point_t), intent(inout) :: key
1162 class(*), intent(inout) :: data
1163
1164 call htable_set(this, key, data)
1165
1166 end subroutine htable_pt_set
1167
1169 function htable_pt_get(this, key, data) result(rcode)
1170 class(htable_pt_t), intent(inout) :: this
1171 type(point_t), intent(inout) :: key
1172 class(*), intent(inout) :: data
1173 integer :: rcode
1174
1175 rcode = htable_get(this, key, data)
1176
1177 end function htable_pt_get
1178
1180 pure function htable_pt_hash(this, k, c) result(hash)
1181 class(htable_pt_t), intent(in) :: this
1182 class(*), intent(in) :: k
1183 integer, value :: c
1184 integer :: hash, i
1185 integer(kind=i8) :: hash2, tmp, mult
1186 integer(kind=i8), parameter :: m1 = int(z'7ed55d15', i8)
1187 integer(kind=i8), parameter :: m2 = int(z'c761c23c', i8)
1188 integer(kind=i8), parameter :: m3 = int(z'165667b1', i8)
1189 integer(kind=i8), parameter :: m4 = int(z'd3a2646c', i8)
1190 integer(kind=i8), parameter :: m5 = int(z'fd7046c5', i8)
1191 integer(kind=i8), parameter :: m6 = int(z'b55a4f09', i8)
1192
1193 select type(k)
1194 type is (point_t)
1195 mult = 1000003
1196 hash2 = int(z'345678')
1197 do i = 1, 3
1198 tmp = transfer(k%x(i), tmp)
1199 tmp = (tmp + m1) + ishft(tmp, 12)
1200 tmp = ieor(ieor(tmp, m2), ishft(tmp, -19))
1201 tmp = (tmp + m3) + ishft(tmp, 5)
1202 tmp = ieor((tmp + m4), ishft(tmp, 9))
1203 tmp = (tmp + m5) + ishft(tmp, 3)
1204 tmp = ieor(ieor(tmp, m6), ishft(tmp, -16))
1205 hash2 = ieor(hash2, tmp) * mult
1206 mult = mult + 82520 + 8
1207 end do
1208 hash2 = hash2 + 97531
1209 hash2 = modulo(hash2 + int(c, i8), int(this%size,i8))
1210 hash = int(hash2, i4)
1211 class default
1212 hash = -1
1213 end select
1214
1215 end function htable_pt_hash
1216
1218 subroutine htable_pt_remove(this, key)
1219 class(htable_pt_t), intent(inout) :: this
1220 type(point_t), intent(inout) :: key
1221
1222 call htable_remove(this, key)
1223
1224 end subroutine htable_pt_remove
1225
1226
1228 subroutine htable_iter_pt_init(this, t)
1229 class(htable_iter_pt_t), intent(inout) :: this
1230 type(htable_pt_t), target, intent(inout) :: t
1231
1232 this%t => t
1233
1234 end subroutine htable_iter_pt_init
1235
1237 subroutine htable_iter_pt_free(this)
1238 type(htable_iter_pt_t), intent(inout) :: this
1239 nullify(this%t)
1240 nullify(this%current)
1241 end subroutine htable_iter_pt_free
1242
1244 function htable_iter_pt_value(this) result(value)
1245 class(htable_iter_pt_t), target, intent(inout) :: this
1246 type(point_t), pointer :: value
1247
1248 select type (hdp => this%current%data)
1249 type is (point_t)
1250 value => hdp
1251 class default
1252 call neko_error('Key and data of different kind (pt)')
1253 end select
1254
1255 end function htable_iter_pt_value
1256
1258 function htable_iter_pt_key(this) result(key)
1259 class(htable_iter_pt_t), target, intent(inout) :: this
1260 type(point_t), pointer :: key
1261
1262 select type (kp => this%current%key)
1263 type is (point_t)
1264 key => kp
1265 class default
1266 call neko_error('Invalid key (pt)')
1267 end select
1268
1269 end function htable_iter_pt_key
1270
1271 !
1272 ! Integer 2-tuple based implementation
1273 !
1275 subroutine htable_i4t2_init(this, size, data)
1276 class(htable_i4t2_t), intent(inout) :: this
1277 integer, value :: size
1278 class(*), intent(inout), optional :: data
1279 type(tuple_i4_t) :: key
1280
1281 if (present(data)) then
1282 call htable_init(this, size, key, data)
1283 else
1284 call htable_init(this, size, key)
1285 end if
1286
1287 end subroutine htable_i4t2_init
1288
1290 subroutine htable_i4t2_set(this, key, data)
1291 class(htable_i4t2_t), intent(inout) :: this
1292 type(tuple_i4_t), intent(inout) :: key
1293 class(*), intent(inout) :: data
1294
1295 call htable_set(this, key, data)
1296
1297 end subroutine htable_i4t2_set
1298
1300 function htable_i4t2_get(this, key, data) result(rcode)
1301 class(htable_i4t2_t), intent(inout) :: this
1302 type(tuple_i4_t), intent(inout) :: key
1303 class(*), intent(inout) :: data
1304 integer :: rcode
1305
1306 rcode = htable_get(this, key, data)
1307
1308 end function htable_i4t2_get
1309
1311 pure function htable_i4t2_hash(this, k, c) result(hash)
1312 class(htable_i4t2_t), intent(in) :: this
1313 class(*), intent(in) :: k
1314 integer, value :: c
1315 integer :: i, hash
1316 integer(kind=i8) :: tmp, hash2, mult
1317 integer(kind=i8), parameter :: m1 = int(z'7ed55d15', i8)
1318 integer(kind=i8), parameter :: m2 = int(z'c761c23c', i8)
1319 integer(kind=i8), parameter :: m3 = int(z'165667b1', i8)
1320 integer(kind=i8), parameter :: m4 = int(z'd3a2646c', i8)
1321 integer(kind=i8), parameter :: m5 = int(z'fd7046c5', i8)
1322 integer(kind=i8), parameter :: m6 = int(z'b55a4f09', i8)
1323
1324 select type(k)
1325 type is (tuple_i4_t)
1326 mult = int(1000003, i8)
1327 hash2 = int(z'345678', i8)
1328 do i = 1, 2
1329 tmp = int(k%x(i), i8)
1330 tmp = (tmp + m1) + ishft(tmp, 12)
1331 tmp = ieor(ieor(tmp, m2), ishft(tmp, -19))
1332 tmp = (tmp + m3) + ishft(tmp, 5)
1333 tmp = ieor((tmp + m4), ishft(tmp, 9))
1334 tmp = (tmp + m5) + ishft(tmp, 3)
1335 tmp = ieor(ieor(tmp, m6), ishft(tmp, -16))
1336 hash2 = ieor(hash2, tmp) * mult
1337 mult = mult + 82520_i8 + 4_i8
1338 end do
1339 hash2 = hash2 + 97531_i8
1340 hash2 = modulo(hash2 + int(c, i8), int(this%size, i8))
1341 hash = int(hash2, i4)
1342 class default
1343 hash = -1
1344 end select
1345 end function htable_i4t2_hash
1346
1348 subroutine htable_i4t2_remove(this, key)
1349 class(htable_i4t2_t), intent(inout) :: this
1350 type(tuple_i4_t), intent(inout) :: key
1351
1352 call htable_remove(this, key)
1353
1354 end subroutine htable_i4t2_remove
1355
1357 subroutine htable_iter_i4t2_init(this, t)
1358 class(htable_iter_i4t2_t), intent(inout) :: this
1359 type(htable_i4t2_t), target, intent(inout) :: t
1360
1361 this%t => t
1362
1363 end subroutine htable_iter_i4t2_init
1364
1366 subroutine htable_iter_i4t2_free(this)
1367 type(htable_iter_i4t2_t), intent(inout) :: this
1368 nullify(this%t)
1369 nullify(this%current)
1370 end subroutine htable_iter_i4t2_free
1371
1373 function htable_iter_i4t2_value(this) result(value)
1374 class(htable_iter_i4t2_t), intent(inout) :: this
1375 type(tuple_i4_t), pointer :: value
1376
1377 select type (hdp => this%current%data)
1378 type is (tuple_i4_t)
1379 value => hdp
1380 class default
1381 call neko_error('Key and data of different kind (i4t2)')
1382 end select
1383
1384 end function htable_iter_i4t2_value
1385
1387 function htable_iter_i4t2_key(this) result(key)
1388 class(htable_iter_i4t2_t), intent(inout) :: this
1389 type(tuple_i4_t), pointer :: key
1390
1391 select type (kp => this%current%key)
1392 type is (tuple_i4_t)
1393 key => kp
1394 class default
1395 call neko_error('Invalid key (i4t2)')
1396 end select
1397
1398 end function htable_iter_i4t2_key
1399
1400 !
1401 ! Integer 4-tuple based implementation
1402 !
1404 subroutine htable_i4t4_init(this, size, data)
1405 class(htable_i4t4_t), intent(inout) :: this
1406 integer, value :: size
1407 class(*), intent(inout), optional :: data
1408 type(tuple4_i4_t) :: key
1409
1410 if (present(data)) then
1411 call htable_init(this, size, key, data)
1412 else
1413 call htable_init(this, size, key)
1414 end if
1415
1416 end subroutine htable_i4t4_init
1417
1419 subroutine htable_i4t4_set(this, key, data)
1420 class(htable_i4t4_t), intent(inout) :: this
1421 type(tuple4_i4_t), intent(inout) :: key
1422 class(*), intent(inout) :: data
1423
1424 call htable_set(this, key, data)
1425
1426 end subroutine htable_i4t4_set
1427
1429 function htable_i4t4_get(this, key, data) result(rcode)
1430 class(htable_i4t4_t), intent(inout) :: this
1431 type(tuple4_i4_t), intent(inout) :: key
1432 class(*), intent(inout) :: data
1433 integer :: rcode
1434
1435 rcode = htable_get(this, key, data)
1436
1437 end function htable_i4t4_get
1438
1440 pure function htable_i4t4_hash(this, k, c) result(hash)
1441 class(htable_i4t4_t), intent(in) :: this
1442 class(*), intent(in) :: k
1443 integer, value :: c
1444 integer :: i, hash
1445 integer(kind=i8) :: tmp, hash2, mult
1446 integer(kind=i8), parameter :: m1 = int(z'7ed55d15', i8)
1447 integer(kind=i8), parameter :: m2 = int(z'c761c23c', i8)
1448 integer(kind=i8), parameter :: m3 = int(z'165667b1', i8)
1449 integer(kind=i8), parameter :: m4 = int(z'd3a2646c', i8)
1450 integer(kind=i8), parameter :: m5 = int(z'fd7046c5', i8)
1451 integer(kind=i8), parameter :: m6 = int(z'b55a4f09', i8)
1452
1453 select type(k)
1454 type is (tuple4_i4_t)
1455 mult = int(1000003, i8)
1456 hash2 = int(z'345678', i8)
1457 do i = 1, 4
1458 tmp = int(k%x(i), i8)
1459 tmp = (tmp + m1) + ishft(tmp, 12)
1460 tmp = ieor(ieor(tmp, m2), ishft(tmp, -19))
1461 tmp = (tmp + m3) + ishft(tmp, 5)
1462 tmp = ieor((tmp + m4), ishft(tmp, 9))
1463 tmp = (tmp + m5) + ishft(tmp, 3)
1464 tmp = ieor(ieor(tmp, m6), ishft(tmp, -16))
1465 hash2 = ieor(hash2, tmp) * mult
1466 mult = mult + 82520_i8 + 8_i8
1467 end do
1468 hash2 = hash2 + 97531_i8
1469 hash2 = modulo(hash2 + int(c, i8), int(this%size, i8))
1470 hash = int(hash2, i4)
1471 class default
1472 hash = -1
1473 end select
1474 end function htable_i4t4_hash
1475
1477 subroutine htable_i4t4_remove(this, key)
1478 class(htable_i4t4_t), intent(inout) :: this
1479 type(tuple4_i4_t), intent(inout) :: key
1480
1481 call htable_remove(this, key)
1482
1483 end subroutine htable_i4t4_remove
1484
1486 subroutine htable_iter_i4t4_init(this, t)
1487 class(htable_iter_i4t4_t), intent(inout) :: this
1488 type(htable_i4t4_t), target, intent(inout) :: t
1489
1490 this%t => t
1491
1492 end subroutine htable_iter_i4t4_init
1493
1495 subroutine htable_iter_i4t4_free(this)
1496 type(htable_iter_i4t4_t), intent(inout) :: this
1497 nullify(this%t)
1498 nullify(this%current)
1499 end subroutine htable_iter_i4t4_free
1500
1502 function htable_iter_i4t4_value(this) result(value)
1503 class(htable_iter_i4t4_t), target, intent(inout) :: this
1504 type(tuple4_i4_t), pointer :: value
1505
1506 select type (hdp => this%current%data)
1507 type is (tuple4_i4_t)
1508 value => hdp
1509 class default
1510 call neko_error('Key and data of different kind (i4t4)')
1511 end select
1512
1513 end function htable_iter_i4t4_value
1514
1516 function htable_iter_i4t4_key(this) result(key)
1517 class(htable_iter_i4t4_t), target, intent(inout) :: this
1518 type(tuple4_i4_t), pointer :: key
1519
1520 ! We should not need this extra select block, and it works great
1521 ! without it for GNU, Intel and NEC, but breaks horribly on Cray
1522 ! (>11.0.x) when using high opt. levels.
1523 select type(hti => this)
1524 type is(htable_iter_i4t4_t)
1525 select type (kp => hti%current%key)
1526 type is (tuple4_i4_t)
1527 key => kp
1528 class default
1529 call neko_error('Invalid key (i4t4)')
1530 end select
1531 class default
1532 call neko_error('Corrupt htable iter. (i4t4)')
1533 end select
1534
1535 end function htable_iter_i4t4_key
1536
1537 !
1538 ! C pointer based implementation
1539 !
1541 subroutine htable_cptr_init(this, size, data)
1542 class(htable_cptr_t), intent(inout) :: this
1543 integer, value :: size
1544 class(*), intent(inout), optional :: data
1545 type(h_cptr_t) :: key
1546
1547 if (present(data)) then
1548 call htable_init(this, size, key, data)
1549 else
1550 call htable_init(this, size, key)
1551 end if
1552
1553 end subroutine htable_cptr_init
1554
1556 subroutine htable_cptr_set(this, key, data)
1557 class(htable_cptr_t), target, intent(inout) :: this
1558 type(h_cptr_t), intent(inout) :: key
1559 class(*), intent(inout) :: data
1560
1561 call htable_set(this, key, data)
1562
1563 end subroutine htable_cptr_set
1564
1566 function htable_cptr_get(this, key, data) result(rcode)
1567 class(htable_cptr_t), target, intent(inout) :: this
1568 type(h_cptr_t), intent(inout) :: key
1569 class(*), intent(inout) :: data
1570 integer :: rcode
1571
1572 rcode = htable_get(this, key, data)
1573
1574 end function htable_cptr_get
1575
1577 pure function htable_cptr_hash(this, k, c) result(hash)
1578 class(htable_cptr_t), intent(in) :: this
1579 class(*), intent(in) :: k
1580 integer, value :: c
1581 integer :: hash
1582 integer(kind=i8) :: k_int
1583
1584 select type(k)
1585 type is (h_cptr_t)
1586 k_int = transfer(k%ptr, k_int)
1587 hash = int(modulo(k_int * 2654435761_i8 + int(c, i8),&
1588 int(this%size, i8)), i4)
1589 class default
1590 hash = -1
1591 end select
1592 end function htable_cptr_hash
1593
1595 subroutine htable_cptr_remove(this, key)
1596 class(htable_cptr_t), target, intent(inout) :: this
1597 type(h_cptr_t), intent(inout) :: key
1598
1599 call htable_remove(this, key)
1600
1601 end subroutine htable_cptr_remove
1602
1604 subroutine htable_iter_cptr_init(this, t)
1605 class(htable_iter_cptr_t), intent(inout) :: this
1606 type(htable_cptr_t), target, intent(inout) :: t
1607
1608 this%t => t
1609
1610 end subroutine htable_iter_cptr_init
1611
1613 subroutine htable_iter_cptr_free(this)
1614 type(htable_iter_cptr_t), intent(inout) :: this
1615 nullify(this%t)
1616 nullify(this%current)
1617 end subroutine htable_iter_cptr_free
1618
1620 function htable_iter_cptr_value(this) result(value)
1621 class(htable_iter_cptr_t), target, intent(inout) :: this
1622 class(*), pointer :: hdp
1623 type(h_cptr_t), pointer :: value
1624
1625 hdp => this%current%data
1626 select type (hdp)
1627 type is (h_cptr_t)
1628 value => hdp
1629 class default
1630 call neko_error('Key and data of different kind (cptr)')
1631 end select
1632
1633 end function htable_iter_cptr_value
1634
1636 function htable_iter_cptr_key(this) result(key)
1637 class(htable_iter_cptr_t), target, intent(inout) :: this
1638 class(*), pointer :: kp
1639 type(h_cptr_t), pointer :: key
1640
1641 kp => this%current%key
1642 select type (kp)
1643 type is (h_cptr_t)
1644 key => kp
1645 class default
1646 call neko_error('Invalid key (cptr)')
1647 end select
1648
1649 end function htable_iter_cptr_key
1650
1651end module htable
Implements a hash table ADT.
Definition htable.f90:52
subroutine htable_i4t4_init(this, size, data)
Initialize an integer 4-tuple hash table.
Definition htable.f90:1405
subroutine htable_iter_r8_init(this, t)
Initialize a double precision based hash table iterator.
Definition htable.f90:1098
subroutine htable_clear(this)
Clear all entries in a hash table.
Definition htable.f90:314
subroutine htable_pt_init(this, size, data)
Initialize a point based hash table.
Definition htable.f90:1145
type(tuple_i4_t) function, pointer htable_iter_i4t2_key(this)
Return the current key of integer based 2-tuple hash table iterator.
Definition htable.f90:1388
subroutine htable_iter_i8_free(this)
Destroy an integer*8 based hash table iterator.
Definition htable.f90:990
subroutine htable_i4_set(this, key, data)
Insert an integer into the hash table.
Definition htable.f90:798
type(tuple4_i4_t) function, pointer htable_iter_i4t4_value(this)
Return the current value of integer based 4-tuple hash table iterator.
Definition htable.f90:1503
integer function, pointer htable_iter_i4_value(this)
Return the current value of the integer based hash table iterator.
Definition htable.f90:874
subroutine htable_r8_init(this, size, data)
Initialize a double precision based hash table.
Definition htable.f90:1037
integer(kind=i8) function, pointer htable_iter_i8_key(this)
Return the current key of the integer*8 based hash table iterator.
Definition htable.f90:1011
type(point_t) function, pointer htable_iter_pt_key(this)
Return the current key of the point based hash table iterator.
Definition htable.f90:1259
pure integer function htable_r8_hash(this, k, c)
Hash function for a double precision based hash table.
Definition htable.f90:1073
subroutine htable_cptr_init(this, size, data)
Initialize a C pointer based hash table.
Definition htable.f90:1542
pure integer function htable_i4_hash(this, k, c)
Hash function for an integer based hash table.
Definition htable.f90:819
subroutine htable_iter_cptr_free(this)
Destroy a C pointer based hash table iterator.
Definition htable.f90:1614
subroutine htable_iter_pt_free(this)
Destroy a point based hash table iterator.
Definition htable.f90:1238
subroutine htable_i4t4_set(this, key, data)
Insert an integer 4-tuple into the hash table.
Definition htable.f90:1420
subroutine htable_i8_init(this, size, data)
Initialize an integer*8 based hash table.
Definition htable.f90:905
subroutine htable_pt_remove(this, key)
Remove a point with key key from the hash table.
Definition htable.f90:1219
subroutine htable_cptr_remove(this, key)
Remove a C pointer with key key from the hash table.
Definition htable.f90:1596
subroutine htable_free(this)
Destroy a hash table.
Definition htable.f90:293
subroutine htable_iter_data(this, data)
Return the data at the current iterator position.
Definition htable.f90:734
pure integer function htable_size(this)
Return total size of htable.
Definition htable.f90:334
subroutine htable_get_data(this, idx, data)
Return data at idx in value.
Definition htable.f90:572
integer function htable_r8_get(this, key, data)
Retrive a double precision float with key key from the hash table.
Definition htable.f90:1062
pure integer function htable_i8_hash(this, k, c)
Hash function for an integer*8 based hash table.
Definition htable.f90:941
subroutine htable_i4t4_remove(this, key)
Remove an integer 4-tuple with key key from the hash table.
Definition htable.f90:1478
integer function htable_get(this, key, data)
Retrieve data associated with key into the hash table.
Definition htable.f90:453
integer function htable_i8_get(this, key, data)
Retrive an integer*8 with key key from the hash table.
Definition htable.f90:930
integer function htable_pt_get(this, key, data)
Retrive a point with key key from the hash table.
Definition htable.f90:1170
subroutine htable_remove(this, key)
Remove a key from the hash table.
Definition htable.f90:486
subroutine htable_set_data(this, idx, data)
Set data at idx to value.
Definition htable.f90:526
real(kind=dp) function, pointer htable_iter_r8_key(this)
Return the current key of the double precision based hash table iterator.
Definition htable.f90:1128
subroutine htable_iter_pt_init(this, t)
Initialize a point based hash table iterator.
Definition htable.f90:1229
integer function htable_i4_get(this, key, data)
Retrive an integer with key key from the hash table.
Definition htable.f90:808
type(h_cptr_t) function, pointer htable_iter_cptr_value(this)
Return the current value of C pointer based hash table iterator.
Definition htable.f90:1621
type(tuple_i4_t) function, pointer htable_iter_i4t2_value(this)
Return the current value of integer based 2-tuple hash table iterator.
Definition htable.f90:1374
logical function htable_iter_next(this)
Advance the iterator to the next valid table entry.
Definition htable.f90:706
integer function htable_cptr_get(this, key, data)
Retrive a C pointer with key key from the hash table.
Definition htable.f90:1567
subroutine htable_i8_set(this, key, data)
Insert an integer*8 into the hash table.
Definition htable.f90:920
subroutine htable_r8_remove(this, key)
Remove a double precision key key from the hash table.
Definition htable.f90:1088
subroutine htable_iter_i4t2_free(this)
Destroy an integer 2-tuple based hash table iterator.
Definition htable.f90:1367
subroutine htable_r8_set(this, key, data)
Insert a double precision key (with data) into the hash table.
Definition htable.f90:1052
type(point_t) function, pointer htable_iter_pt_value(this)
Return the current value of the point based hash table iterator.
Definition htable.f90:1245
integer function htable_i4t4_get(this, key, data)
Retrive an integer 4-tuple with key key from the hash table.
Definition htable.f90:1430
subroutine htable_i4t2_set(this, key, data)
Insert an integer 2-tuple into the hash table.
Definition htable.f90:1291
pure integer function htable_num_entries(this)
Return number of entries in the table.
Definition htable.f90:327
type(tuple4_i4_t) function, pointer htable_iter_i4t4_key(this)
Return the current key of integer based 4-tuple hash table iterator.
Definition htable.f90:1517
recursive subroutine htable_set(this, key, data)
Insert tuple (key, value) into the hash table.
Definition htable.f90:342
pure logical function htable_eq_key(this, idx, key)
Compare key at idx to key.
Definition htable.f90:616
subroutine htable_i4t2_remove(this, key)
Remove an integer 2-tuple with key key from the hash table.
Definition htable.f90:1349
subroutine htable_set_key(this, idx, key)
Set key at idx to key.
Definition htable.f90:660
subroutine htable_iter_i8_init(this, t)
Initialize an integer*8 based hash table iterator.
Definition htable.f90:981
pure integer function htable_i4t4_hash(this, k, c)
Hash function for an integer 4-tuple hash table.
Definition htable.f90:1441
pure integer function htable_pt_hash(this, k, c)
Hash function for a point based hash table.
Definition htable.f90:1181
integer function, pointer htable_iter_i4_key(this)
Return the current key of the integer based hash table iterator.
Definition htable.f90:888
subroutine htable_iter_i4_init(this, t)
Initialize an integer based hash table iterator.
Definition htable.f90:858
subroutine htable_init(this, size, key, data)
Initialize a hash table of type data.
Definition htable.f90:259
subroutine htable_i4t2_init(this, size, data)
Initialize an integer 2-tuple hash table.
Definition htable.f90:1276
subroutine htable_cptr_set(this, key, data)
Insert a C pointer into the hash table.
Definition htable.f90:1557
subroutine htable_iter_i4t4_free(this)
Destroy an integer 4-tuple based hash table iterator.
Definition htable.f90:1496
subroutine htable_i4_remove(this, key)
Remove an integer with key key from the hash table.
Definition htable.f90:849
subroutine htable_iter_cptr_init(this, t)
Initialize a C pointer based hash table iterator.
Definition htable.f90:1605
integer(kind=i8) function, pointer htable_iter_i8_value(this)
Return the current value of the integer*8 based hash table iterator.
Definition htable.f90:997
integer function htable_i4t2_get(this, key, data)
Retrive an integer 2-tuple with key key from the hash table.
Definition htable.f90:1301
subroutine htable_iter_i4t4_init(this, t)
Initialize an integer 4-tuple based hash table iterator.
Definition htable.f90:1487
subroutine htable_i8_remove(this, key)
Remove an integer*8 with key key from the hash table.
Definition htable.f90:972
subroutine htable_i4_init(this, size, data)
Initialize an integer based hash table.
Definition htable.f90:783
pure integer function htable_cptr_hash(this, k, c)
Hash function for an integer 4-tuple hash table.
Definition htable.f90:1578
subroutine htable_pt_set(this, key, data)
Insert a point key (with data) into the hash table.
Definition htable.f90:1160
subroutine htable_iter_reset(this)
Reset an iterator.
Definition htable.f90:725
subroutine htable_iter_i4_free(this)
Destroy an integer based hash table iterator.
Definition htable.f90:867
type(h_cptr_t) function, pointer htable_iter_cptr_key(this)
Return the current key of a C pointer based hash table iterator.
Definition htable.f90:1637
subroutine htable_iter_r8_free(this)
Destroy a double precision based hash table iterator.
Definition htable.f90:1107
pure integer function htable_i4t2_hash(this, k, c)
Hash function for an integer 2-tuple hash table.
Definition htable.f90:1312
subroutine htable_iter_i4t2_init(this, t)
Initialize an integer 2-tuple based hash table iterator.
Definition htable.f90:1358
real(kind=dp) function, pointer htable_iter_r8_value(this)
Return the current value of the double precision based hash table iterator.
Definition htable.f90:1114
Definition math.f90:60
real(kind=rp), parameter, public neko_m_ln2
Definition math.f90:73
integer, parameter, public i8
Definition num_types.f90:7
integer, parameter, public i4
Definition num_types.f90:6
integer, parameter, public dp
Definition num_types.f90:9
Implements a point.
Definition point.f90:35
Implements a n-tuple.
Definition tuple.f90:41
Utilities.
Definition utils.f90:35
Hash table entry, tuple (key, data)
Definition htable.f90:63
C pointer based hash table.
Definition htable.f90:162
Integer based hash table.
Definition htable.f90:102
Integer 2-tuple based hash table.
Definition htable.f90:142
Integer 4-tuple based hash table.
Definition htable.f90:152
Integer*8 based hash table.
Definition htable.f90:112
Iterator for a C pointer based hash table.
Definition htable.f90:240
Iterator for an integer based hash table.
Definition htable.f90:186
Iterator for an integer based 2-tuple hash table.
Definition htable.f90:222
Iterator for an integer based 4-tuple hash table.
Definition htable.f90:231
Iterator for an integer*8 based hash table.
Definition htable.f90:195
Iterator for a point based hash table.
Definition htable.f90:213
Iterator for a double precision based hash table.
Definition htable.f90:204
Base type for a hash table iterator.
Definition htable.f90:176
Point based hash table.
Definition htable.f90:132
Double precision based hash table.
Definition htable.f90:122
Base type for a hash table.
Definition htable.f90:73
A point in with coordinates .
Definition point.f90:43
Integer based 4-tuple.
Definition tuple.f90:76
Integer based 2-tuple.
Definition tuple.f90:58
Base type for an n-tuple.
Definition tuple.f90:48