Как сделать выделение указателей в подпрограммах при использовании OpenMP? - PullRequest
1 голос
/ 23 декабря 2011

Как показывает следующий пример кода, основная программа пытается использовать OpenMP для вызова подпрограммы.В этой подпрограмме локальная переменная-указатель создается и повторяется.Программа генерирует Subscript #1 of the array PTEMPINTLIST has value 208 which is greater than the upper bound of 207 ошибок (конкретные цифры различаются).Я уже сделал охватывающий пользовательский тип omp-private, но кажется, что локальные переменные в вызванных подпрограммах также должны быть объявлены omp-private, но я не уверен, верно ли это, и я не знаю, как этого добитьсяэтот.

Не могли бы вы прокомментировать, почему программа выдает такую ​​ошибку?Что еще более важно, не могли бы вы прокомментировать лучшие практики, касающиеся того, как сделать распределение указателей в подпрограммах при использовании OpenMP?

Не представляете, почему код на фортране не окрашен.Может кто-нибудь помочь прокомментировать, как раскрасить код, чтобы он был более читабельным?

Компилятор - Intel Fortran Compiler, и его версия выглядит следующим образом:

[root@localhost new]# ifort --version
ifort (IFORT) 12.1.0 20111011
Copyright (C) 1985-2011 Intel Corporation.  All rights reserved.

Ошибкасообщение показано ниже:

[root@localhost new]# ifort test_omp.f90 -warn -check -g -trace -openmp -static
[root@localhost new]# ./a.out 
 Thread numbers are:            8
 Thread            0  -            1
 Thread            0  -            2
 Thread            0  -            3
 Thread            0  -            4
 Thread            0  -            5
 Thread            0  -            6
 Thread            0  -            7
 Thread            0  -            8
 Thread            0  -            9
 Thread            0  -           10
 Thread numbers are:            8
 Thread            7  -            1
 Thread            7  -            2
 Thread            7  -            3
 Thread            7  -            4
 Thread            7  -            5
 Thread            7  -            6
 Thread            7  -            7
 Thread            7  -            8
 Thread            7  -            9
 Thread            7  -           10
 Thread            7  -           11
 Thread            7  -           12
 Thread            7  -           13
 Thread            7  -           14
 Thread            7  -           15
 Thread            7  -           16
 Thread            7  -           17
 Thread            7  -           18
 Thread            7  -           19
 Thread            7  -           20
 Thread            7  -           21
 Thread            7  -           22
 Thread            7  -           23
 Thread            7  -           24
 Thread            7  -           25
 Thread            7  -           26
 Thread            7  -           27
 Thread            7  -           28
 Thread            7  -           29
 Thread            7  -           30
 Thread            7  -           31
 Thread            7  -           32
 Thread            7  -           33
 Thread            7  -           34
 Thread            7  -           35
 Thread            7  -           36
 Thread            7  -           37
 Thread            7  -           38
 Thread            7  -           39
 Thread            7  -           40
 Thread            7  -           41
 Thread            7  -           42
 Thread            7  -           43
 Thread            7  -           44
 Thread            7  -           45
 Thread            7  -           46
 Thread            7  -           47
 Thread            7  -           48
 Thread            7  -           49
 Thread            7  -           50
 Thread            7  -           51
 Thread            7  -           52
 Thread            7  -           53
 Thread            7  -           54
 Thread            7  -           55
 Thread            7  -           56
 Thread            7  -           57
 Thread            7  -           58
 Thread            7  -           59
 Thread            7  -           60
 Thread            7  -           61
 Thread            7  -           62
 Thread            7  -           63
 Thread            7  -           64
 Thread            7  -           65
 Thread            7  -           66
 Thread            7  -           67
 Thread            7  -           68
 Thread            7  -           69
 Thread            7  -           70
 Thread            7  -           71
 Thread            7  -           72
 Thread            7  -           73
 Thread            7  -           74
 Thread            7  -           75
 Thread            7  -           76
 Thread            7  -           77
 Thread            7  -           78
 Thread            7  -           79
 Thread            7  -           80
 Thread            7  -           81
 Thread            7  -           82
 Thread            7  -           83
 Thread            7  -           84
 Thread            7  -           85
 Thread            7  -           86
 Thread            7  -           87
 Thread            7  -           88
 Thread            7  -           89
 Thread            7  -           90
 Thread            7  -           91
 Thread            7  -           92
 Thread            7  -           93
 Thread            7  -           94
 Thread            7  -           95
 Thread            7  -           96
 Thread            7  -           97
 Thread            7  -           98
 Thread            7  -           99
 Thread            7  -          100
 Thread            7  -          101
 Thread            7  -          102
 Thread            7  -          103
 Thread            7  -          104
 Thread            7  -          105
 Thread            7  -          106
 Thread            7  -          107
 Thread            7  -          108
 Thread            7  -          109
 Thread            7  -          110
 Thread            7  -          111
 Thread            7  -          112
 Thread            7  -          113
 Thread            7  -          114
 Thread            7  -          115
 Thread            7  -          116
 Thread            7  -          117
 Thread            7  -          118
 Thread            7  -          119
 Thread            7  -          120
 Thread            7  -          121
 Thread            7  -          122
 Thread            7  -          123
 Thread            7  -          124
 Thread            7  -          125
 Thread            7  -          126
 Thread            7  -          127
 Thread            7  -          128
 Thread            7  -          129
 Thread            7  -          130
 Thread            7  -          131
 Thread            7  -          132
 Thread            7  -          133
 Thread            7  -          134
 Thread            7  -          135
 Thread            7  -          136
 Thread            7  -          137
 Thread            7  -          138
 Thread            7  -          139
 Thread            7  -          140
 Thread            7  -          141
 Thread            7  -          142
 Thread            7  -          143
 Thread            7  -          144
 Thread            7  -          145
 Thread            7  -          146
 Thread            7  -          147
 Thread            7  -          148
 Thread            7  -          149
 Thread            7  -          150
 Thread            7  -          151
 Thread            7  -          152
 Thread            7  -          153
 Thread            7  -          154
 Thread            7  -          155
 Thread            7  -          156
 Thread            7  -          157
 Thread            7  -          158
 Thread            7  -          159
 Thread            7  -          160
 Thread            7  -          161
 Thread            7  -          162
 Thread            7  -          163
 Thread            7  -          164
 Thread            7  -          165
 Thread            7  -          166
 Thread            7  -          167
 Thread            7  -          168
 Thread            7  -          169
 Thread            7  -          170
 Thread            7  -          171
 Thread            7  -          172
 Thread            7  -          173
 Thread            7  -          174
 Thread            7  -          175
 Thread            7  -          176
 Thread            7  -          177
 Thread            7  -          178
 Thread            7  -          179
 Thread            7  -          180
 Thread            7  -          181
 Thread            7  -          182
 Thread            7  -          183
 Thread            7  -          184
 Thread            7  -          185
 Thread            7  -          186
 Thread            7  -          187
 Thread            7  -          188
 Thread            7  -          189
 Thread            7  -          190
 Thread            7  -          191
 Thread            7  -          192
 Thread            7  -          193
 Thread            7  -          194
 Thread            7  -          195
 Thread            7  -          196
 Thread            7  -          197
 Thread            7  -          198
 Thread            7  -          199
 Thread            7  -          200
 Thread            7  -          201
 Thread            7  -          202
 Thread            7  -          203
 Thread            7  -          204
 Thread            7  -          205
 Thread            7  -          206
 Thread            7  -          207
forrtl: severe (408): fort: (2): Subscript #1 of the array PTEMPINTLIST has value 208 which is greater than the upper bound of 207

Image              PC                Routine            Line        Source             
a.out              00000000004F0C6A  Unknown               Unknown  Unknown
a.out              00000000004EF766  Unknown               Unknown  Unknown
a.out              0000000000426700  Unknown               Unknown  Unknown
a.out              000000000040235F  Unknown               Unknown  Unknown
a.out              0000000000402881  Unknown               Unknown  Unknown
a.out              0000000000400D09  testopenmp_1_allo          39  omp.f90
a.out              00000000004006BE  MAIN__                     23  omp.f90
a.out              00000000004A4CF3  Unknown               Unknown  Unknown

Пример кода:

    module MyModule
        type :: MyType
            integer, dimension(:), pointer :: pIntList => null ()
        end type 
    end module MyModule

    program TestOpenMP_1_AllocationWithinSubroutines

        use MyModule
        use omp_lib
        implicit none

        type(MyType) :: instance
        integer :: threadCount 
        integer :: threadId 
        integer :: I

!$omp parallel private (instance, threadCount, threadId, I)
        threadCount = OMP_GET_NUM_THREADS()
        write (*,*) 'Thread numbers are: ', threadCount
        threadId = OMP_GET_THREAD_NUM()
        allocate (instance%pIntList(200 + threadId))
        CALL IterateList(instance) 
!$omp end parallel

        read (*,*)

    contains

        subroutine IterateList(aInstance)
            type(MyType) :: aInstance
            integer, dimension(:), pointer :: pTempIntList => null()
            integer :: threadId
            threadId = OMP_GET_THREAD_NUM()
            allocate (pTempIntList(size(aInstance%pIntList)))
            do I = 1, size(pTempIntList)
                pTempIntList(I) = I 
                !write (*,*) pTempIntList(I)
                write (*,*) 'Thread ',threadId, ' - ',pTempIntList(I)
            end do          
        end subroutine 

    end program TestOpenMP_1_AllocationWithinSubroutines

Ответы [ 2 ]

3 голосов
/ 23 декабря 2011

С подпрограммой, содержащейся в основной программе, gfortran выдает сообщение об ошибке: «В строке 36 файла test_OpenMP.f90 / Ошибка времени выполнения Fortran: переменная цикла была изменена»

Очевидно, что размер "pTempIntList" всегда установлен на одно и то же значение (варьируется между прогонами), очевидно, используя размер (aInstance% pIntList) для случайного потока. Который слишком мал для нитей, прошедших эту нить. Ниже приведена версия, которая работает. Удаление "=> null ()" представляется необходимым как для gfortran, так и для ifort. Я не знаю, так ли это, но так как этого требуют два компилятора ...

Попробуйте эту версию:

module MyModule
  type :: MyType
      integer, dimension(:), pointer :: pIntList
  end type

contains
   subroutine IterateList(aInstance)
      use omp_lib
      integer :: I
      type(MyType) :: aInstance
      integer, dimension(:), pointer :: pTempIntList
      integer :: threadId
      threadId = OMP_GET_THREAD_NUM()
      allocate (pTempIntList(size(aInstance%pIntList)))
      do I = 1, size(pTempIntList)
          write (*, *) i, threadID, size(aInstance%pIntList), size (pTempIntList)
          pTempIntList(I) = I
      end do
   end subroutine IterateList

end module MyModule

program TestOpenMP_1_AllocationWithinSubroutines

   use MyModule
   use omp_lib
   implicit none

   type(MyType) :: instance
   integer :: threadCount
   integer :: threadId
   integer :: I

   !$omp parallel private (instance, threadCount, threadId, I)
   threadCount = OMP_GET_NUM_THREADS()
   write (*,*) 'Thread numbers are: ', threadCount
   threadId = OMP_GET_THREAD_NUM()
   allocate (instance%pIntList(200 + threadId))
   CALL IterateList(instance)
   !$omp end parallel

end program TestOpenMP_1_AllocationWithinSubroutines
2 голосов
/ 23 декабря 2011

Я думаю, что вы столкнулись с проблемой, что инициализация переменной дает ей атрибут save.Инициализация pTempIntList с нулевым указателем означает, что он сохраняется между различными вызовами подпрограммы.Я не уверен в деталях реализации, но можно предположить, что все вызовы подпрограммы фактически разделяют память для этой переменной.

Вы также должны серьезно рассмотреть комментарий Anycorn.Обычно гораздо безопаснее использовать размещаемые переменные, чем указатели.Если это можно сделать с помощью выделяемых ресурсов, используйте их.

...