1

如以下代码示例所示,主程序尝试利用 OpenMP 调用子程序。在该子例程中,创建并迭代了一个局部指针变量。程序会产生Subscript #1 of the array PTEMPINTLIST has value 208 which is greater than the upper bound of 207错误(具体数字不同)。我已经制作了包含用户派生类型omp-private,但似乎调用的子例程中的局部变量也应该声明omp-private,但我不确定这是否属实,我不知道如何实现这一点。

你能帮忙评论一下为什么程序会出现这样的错误吗?更重要的是,您能否帮助评论有关在使用 OpenMP 时如何在子例程中分配指针的最佳实践?

不知道为什么 fortran 代码没有着色。有人可以帮助评论如何为代码着色,使其更具可读性吗?

编译器为 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
4

2 回答 2

3

随着主程序中包含的子程序 gfortran 给出错误消息:“在文件 test_OpenMP.f90 / Fortran 运行时错误的第 36 行:循环变量已被修改”

显然,“pTempIntList”的大小始终设置为相同的值(在运行之间变化),显然将 size(aInstance%pIntList) 用于随机线程。对于超过该线程的线程来说,这太小了。下面是一个有效的版本。对于 gfortran 和 ifort,删除“=> null ()”似乎是必要的。我不知道这是否应该是这种情况,但由于两个编译器需要它......

试试这个版本:

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
于 2011-12-23T04:23:16.260 回答
2

我认为您遇到了变量初始化赋予它save属性的问题。使用空指针初始化pTempIntList意味着它在子例程的不同调用之间被保存。我不确定实现的细节,但猜测可能是子例程的所有调用实际上共享此变量的内存。

你真的应该认真考虑 Anycorn 的评论。使用可分配变量通常比使用指针更安全。如果可以使用可分配对象来完成,请使用它们。

于 2011-12-23T16:07:22.813 回答