发明名称 基于OpenCL的GPU加速三维时域有限差分电磁场仿真的方法
摘要 本发明提出一种基于OpenCL的GPU加速三维时域有限差分(FDTD)电磁场仿真的方法,应用于电磁场仿真分析领域,利用OpenCL简化FDTD方法对电磁场仿真的设计与实现。首先设置FDTD仿真参数并动态申请内存空间,构建三维的电磁模型并进行网格剖分,然后初始化OpenCL的计算参数,对三维电磁模型基于OpenCL进行FDTD加速仿真,最后用OpenCL标准库函数释放显存中存储的数据,释放CPU内存资源。本发明方法显著提升了FDTD电磁场仿真速度,与利用CPU计算相比速度提升可达5-10倍,且具有UPML吸收边界条件,可以模拟电磁波在自由空间的传播,使得FDTD电磁场仿真具有更广泛的实际应用。
申请公布号 CN102207987B 申请公布日期 2012.11.21
申请号 CN201110144446.8 申请日期 2011.05.31
申请人 中国航天标准化研究所 发明人 代健;褚天舒
分类号 G06F17/50(2006.01)I 主分类号 G06F17/50(2006.01)I
代理机构 北京永创新实专利事务所 11121 代理人 周长琪
主权项 1.一种基于OpenCL的GPU加速三维时域有限差分电磁场仿真的方法,其特征在于,该方法具体包括以下步骤:步骤1:设置FDTD仿真参数,为所述仿真参数动态申请内存空间;步骤1具体包括:步骤1-1:设置电磁场仿真参数,包括如下步骤:步骤1-1-1:设置空间步长Δα:<maths num="0001"><![CDATA[<math><mrow><mi>&Delta;&alpha;</mi><mo>=</mo><mfrac><msub><mi>&lambda;</mi><mi>m</mi></msub><mn>10</mn></mfrac><mo>,</mo><mi>&alpha;</mi><mo>=</mo><mi>x</mi><mo>,</mo><mi>y</mi><mo>,</mo><mi>z</mi><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>1</mn><mo>)</mo></mrow></mrow></math>]]></maths>λ<sub>m</sub>为激励源的最高频率所对应的波长;步骤1-1-2:设置时间步长Δt,时间步长Δt的设置满足式(2):<maths num="0002"><![CDATA[<math><mrow><mi>&Delta;t</mi><mo>=</mo><mfrac><mn>0.9</mn><mrow><mi>c</mi><msqrt><mfrac><mn>1</mn><mrow><mi>&Delta;</mi><msup><mi>x</mi><mn>2</mn></msup></mrow></mfrac><mo>+</mo><mfrac><mn>1</mn><mrow><mi>&Delta;</mi><msup><mi>y</mi><mn>2</mn></msup></mrow></mfrac><mo>+</mo><mfrac><mn>1</mn><mrow><mi>&Delta;</mi><msup><mi>z</mi><mn>2</mn></msup></mrow></mfrac></msqrt></mrow></mfrac><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>2</mn><mo>)</mo></mrow></mrow></math>]]></maths>c为真空中的光速;步骤1-1-3:设置UPML吸收边界:设置UPML吸收边界在x-y-z三维方向的网格层数n<sub>x-PML1</sub>,n<sub>x-PML2</sub>,n<sub>y-PML1</sub>,n<sub>y-PML2</sub>,n<sub>z-PML1</sub>和n<sub>z-PML2</sub>,以及吸收边界参数σ和κ;步骤1-1-4:激励源设置,包括电流源设置与偶极子源设置;电流源设置:在麦克斯韦磁场旋度方程的右侧添加电流密度项,如式(3)所示,根据实际情况,选择在x-y-z三维方向的其中一个方向上施加该电流源:<maths num="0003"><![CDATA[<math><mrow><mo>&dtri;</mo><mo>&times;</mo><mover><mi>H</mi><mo>&RightArrow;</mo></mover><mo>=</mo><mfrac><mrow><mo>&PartialD;</mo><mover><mi>D</mi><mo>&RightArrow;</mo></mover></mrow><mrow><mo>&PartialD;</mo><mi>t</mi></mrow></mfrac><mo>+</mo><mover><mi>J</mi><mo>&RightArrow;</mo></mover><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>3</mn><mo>)</mo></mrow></mrow></math>]]></maths>其中,▽表示旋度符号,<img file="FDA00002097791300014.GIF" wi="33" he="47" />为电流密度矢量,<img file="FDA00002097791300015.GIF" wi="42" he="45" />为磁场矢量,<img file="FDA00002097791300016.GIF" wi="37" he="45" />为电位移矢量,t为时间;偶极子源设置:在麦克斯韦磁场旋度方程的右侧施加电偶极子项,如式(4)所示,根据实际情况,选择在x-y-z三维方向的其中一个方向上施加该偶极子源:<maths num="0004"><![CDATA[<math><mrow><mo>&dtri;</mo><mo>&times;</mo><mover><mi>H</mi><mo>&RightArrow;</mo></mover><mo>=</mo><mi>&epsiv;</mi><mfrac><mrow><mo>&PartialD;</mo><mover><mi>E</mi><mo>&RightArrow;</mo></mover></mrow><mrow><mo>&PartialD;</mo><mi>t</mi></mrow></mfrac><mo>+</mo><mfrac><mn>1</mn><mrow><mi>&Delta;</mi><msup><mi>&alpha;</mi><mn>3</mn></msup></mrow></mfrac><mfrac><mrow><mi>d</mi><mover><mi>p</mi><mo>&RightArrow;</mo></mover></mrow><mi>dt</mi></mfrac><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>4</mn><mo>)</mo></mrow></mrow></math>]]></maths>其中,<img file="FDA00002097791300018.GIF" wi="29" he="45" />表示偶极子源矢量,<img file="FDA00002097791300019.GIF" wi="33" he="45" />表示电场矢量,ε表示介电常数;步骤1-2:动态申请内存空间:采用动态分配方式,连续存储数据,对于三维电磁场数据变量以及由UPML引入的三维临时电磁参量,其寻址方式为:φ[i×N<sub>yz</sub>+j×N<sub>z</sub>+k],N<sub>yz</sub>=N<sub>y</sub>×N<sub>z</sub>          (5)其中i,j和k为分别代表三维坐标系x轴、y轴和z轴上所对应的空间位置点,N<sub>y</sub>和N<sub>z</sub>为y轴和z轴上所对应的网格数;步骤2:构建三维的电磁模型,对该电磁模型进行网格剖分;步骤3:初始化OpenCL的计算参数,包括:获得FDTD仿真空间的大小、设置仿真所用处理器类型、创建上下文、获得工作组的维数及大小信息、创建指令序列及数据缓存区、装载FDTD加速程序文件、声明磁场仿真计算的内核函数以及电场仿真计算的内核函数;步骤4:基于OpenCL对三维电磁模型进行FDTD加速仿真;步骤4包括以下步骤:步骤4-1:设置时间迭代步数n,则总的迭代时间为t=n×Δt;步骤4-2:为每一个迭代步设置其对应的开始时间:t<sub>0</sub>+Δt×(n-1),其中t<sub>0</sub>为仿真起始时刻;步骤4-3:按照步骤1中的激励源设置方法设置激励源;步骤4-4:执行基于OpenCL的FDTD磁场仿真计算内核函数:步骤4-4-1:在时间步n=1时,利用OpenCL标准库函数clSetKernelArg()取得FDTD磁场仿真计算所用的三维电磁场数据变量以及三维临时电磁参量的存储地址;步骤4-4-2:当基于GPU进行仿真时,利用OpenCL标准库函数clEnqueueWriteBuffer(),将指令序列数据缓冲区中FDTD磁场仿真计算所用的三维电磁场数据变量以及三维临时电磁参量传递到GPU显存;步骤4-4-3:利用OpenCL标准库函数clEnqueueNDRangeKernel()激活GPU内核,进行FDTD磁场加速仿真;步骤4-4-3包括如下步骤:步骤4-4-3-1:设置工作组大小为:n<sub>x</sub>×n<sub>y</sub>×n<sub>z</sub>=2×2×30;步骤4-4-3-2:设置全局存储空间为整个FDTD仿真空间的大小,本地存储空间为每个工作组的大小,每个FDTD立方体网格具体位置坐标(I<sub>x</sub>,I<sub>y</sub>,I<sub>z</sub>)为:<maths num="0005"><![CDATA[<math><mrow><mfenced open='{' close=''><mtable><mtr><mtd><msub><mi>I</mi><mi>x</mi></msub><mo>=</mo><msub><mi>j</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>x</mi></msub><mo>+</mo><msub><mi>i</mi><mi>x</mi></msub></mtd></mtr><mtr><mtd><msub><mi>I</mi><mi>y</mi></msub><mo>=</mo><msub><mi>j</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub></mtd></mtr><mtr><mtd><msub><mi>I</mi><mi>z</mi></msub><mo>=</mo><msub><mi>j</mi><mi>z</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr></mtable></mfenced><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>6</mn><mo>)</mo></mrow></mrow></math>]]></maths>其中,j<sub>x</sub>,j<sub>y</sub>,j<sub>z</sub>为边长与空间步长相等的立方体网格Δα<sup>3</sup>所在的工作组对应的空间位置;n<sub>x</sub>,n<sub>y</sub>,n<sub>z</sub>为工作组沿三维的网格数;i<sub>x</sub>,i<sub>y</sub>,i<sub>z</sub>为立方体网格Δα<sup>3</sup>在工作组内部所对应的具体位置坐标;步骤4-4-3-3:通过式(7)确定全局存储空间的位置坐标代号i000、i100、i010与i001:<maths num="0006"><![CDATA[<math><mrow><mfenced open='{' close=''><mtable><mtr><mtd><mi>i</mi><mn>000</mn><mo>=</mo><msub><mi>I</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>i</mi><mn>100</mn><mo>=</mo><mrow><mo>(</mo><msub><mi>I</mi><mi>x</mi></msub><mo>+</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>i</mi><mn>010</mn><mo>=</mo><msub><mi>I</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><mrow><mo>(</mo><msub><mi>I</mi><mi>y</mi></msub><mo>+</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>i</mi><mn>001</mn><mo>=</mo><msub><mi>I</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub><mo>+</mo><mn>1</mn></mtd></mtr></mtable></mfenced><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>7</mn><mo>)</mo></mrow></mrow></math>]]></maths>N<sub>y</sub>和N<sub>z</sub>为整个FDTD仿真空间y轴和z轴方向所对应的网格;通过式(8)确定本地存储空间的位置坐标代号localindex、local100、local010和local001:<maths num="0007"><![CDATA[<math><mrow><mfenced open='{' close=''><mtable><mtr><mtd><mi>localindex</mi><mo>=</mo><msub><mi>i</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>local</mi><mn>100</mn><mo>=</mo><mrow><mo>(</mo><msub><mi>i</mi><mi>x</mi></msub><mo>+</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>local</mi><mn>010</mn><mo>=</mo><msub><mi>i</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><mrow><mo>(</mo><msub><mi>i</mi><mi>y</mi></msub><mo>+</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>local</mi><mn>001</mn><mo>=</mo><msub><mi>i</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub><mo>+</mo><mn>1</mn></mtd></mtr></mtable></mfenced><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>8</mn><mo>)</mo></mrow></mrow></math>]]></maths>步骤4-4-3-4:将GPU全局存储空间的电磁场数据及相关的三维临时电磁参量传递到本地存储空间;步骤4-4-3-5:将三维磁场空间位置坐标的循环迭代转化为基于OpenCL的并行计算;(1)y轴方向E<sub>x</sub>和E<sub>z</sub>的数据转化过程:首先判断该网格处的坐标I<sub>y</sub>是否小于全局存储空间Y轴坐标上限(N<sub>y</sub>-1),若否,则将E<sub>x-010</sub>和E<sub>z-010</sub>都设置为float4[1.0,1.0,1.0,1.0];若是,则进一步判断本地存储空间的网格坐标i<sub>y</sub>是否小于本地存储空间y轴纵坐标上限(n<sub>y</sub>-1),若否,则将E<sub>x-010</sub>和E<sub>z-010</sub>分别设置为E<sub>x</sub>[i010]和E<sub>z</sub>[i010],若是,则将E<sub>x-010</sub>和E<sub>z-010</sub>分别设置为E<sub>x-l</sub>[local010]和E<sub>z-l</sub>[local010];其中E<sub>x-010</sub>和E<sub>z-010</sub>的下角标010表示电场数据在y轴方向后移一位;(2)z轴方向E<sub>x</sub>和E<sub>y</sub>的数据转化过程:首先,判断该网格处的纵坐标I<sub>z</sub>是否小于全局存储空间z轴坐标上限(N<sub>z</sub>/4-1),若不是,则将E<sub>x-001</sub>设置为float4(E<sub>x-l</sub>[localindex].y,E<sub>x-l</sub>[localindex].z,E<sub>x-l</sub>[localindex].w,1.0),将E<sub>y-001</sub>设置为float4(E<sub>y-l</sub>[localindex].y,E<sub>y-l</sub>[localindex].z,E<sub>y-l</sub>[localindex].w,1.0);若是,则进一步判断本地存储空间的网格坐标i<sub>z</sub>是否小于本地存储空间z轴坐标上限(n<sub>z</sub>-1),若否,则将E<sub>x-001</sub>和E<sub>y-001</sub>分别设置为float4(E<sub>x-l</sub>[localindex].y,E<sub>x-l</sub>[localindex].z,E<sub>x-l</sub>[localindex].w,E<sub>x-l</sub>[i001].x)和float4(E<sub>y-l</sub>[localindex].y,E<sub>y-l</sub>[localindex].z,E<sub>y-l</sub>[localindex].w,E<sub>y-l</sub>[i001].x),若是,则设置E<sub>x-001</sub>为float4(E<sub>x-l</sub>[localindex].y,E<sub>x-l</sub>[localindex].z,E<sub>x-l</sub>[localindex].w,E<sub>x-l</sub>[local001].x),设置E<sub>y-001</sub>为float4(E<sub>y-l</sub>[localindex].y,E<sub>y-l</sub>[localindex].z,E<sub>y-l</sub>[localindex].w,E<sub>y-l</sub>[local001].x);其中.x、.y、.z和.w依次表示float4型数据中4个float型数据,E<sub>x-001</sub>和E<sub>y-001</sub>的下角标001表示电场数据在z轴方向后移一位;(3)x轴方向E<sub>y</sub>和E<sub>z</sub>数据转化过程:首先判断该网格处的坐标I<sub>x</sub>是否小于全局存储空间x轴坐标上限(N<sub>x</sub>-1),若否,则将E<sub>y-100</sub>和E<sub>z-100</sub>都设置为float4[1.0,1.0,1.0,1.0];若是,则进一步判断本地存储空间的网格坐标i<sub>x</sub>是否小于本地存储空间x轴纵坐标上限(n<sub>x</sub>-1),若否,则将E<sub>y-100</sub>和E<sub>z-100</sub>分别设置为E<sub>y</sub>[i100]和E<sub>z</sub>[i100],若是,则将E<sub>y-100</sub>和E<sub>z-100</sub>分别设置为E<sub>y-l</sub>[local100]和E<sub>z-l</sub>[local100];其中E<sub>y-100</sub>和E<sub>z-100</sub>的下角标100表示电场数据在x轴方向后移一位;步骤4-4-3-6:确定x方向的磁场H<sub>x</sub>、y方向的磁场H<sub>y</sub>与z方向的磁场H<sub>z</sub>;步骤4-4-4:如果需要对仿真后的磁场数据进行存储,则利用OpenCL标准库函数clEnqueueReadBuffer()将x方向、y方向、z方向的磁场H<sub>x</sub>、H<sub>y</sub>、H<sub>z</sub>由GPU显存传递到CPU内存,以便在内存中对磁场数据进行后处理;步骤4-5:执行基于OpenCL的FDTD电场仿真计算内核函数:步骤4-5-1:在时间步n=1时,利用OpenCL标准库函数clSetKernelArg()取得FDTD电场仿真计算所用的三维电磁场数据变量以及三维临时电磁参量的存储地址;步骤4-5-2:当基于GPU进行仿真时,利用OpenCL标准库函数clEnqueueWriteBuffer(),将指令序列数据缓冲区中FDTD电场计算所用的三维电磁场数据变量以及三维临时电磁参量传递到GPU显存;步骤4-5-3:利用OpenCL标准库函数clEnqueueNDRangeKernel()激活GPU内核进行FDTD电场加速仿真;步骤4-5-3包括如下步骤:步骤4-5-3-1:设置全局存储空间为整个FDTD仿真空间的大小,本地存储空间为每个工作组的大小,每个FDTD立方体网格具体位置坐标(I<sub>x</sub>,I<sub>y</sub>,I<sub>z</sub>)为:<maths num="0008"><![CDATA[<math><mrow><mfenced open='{' close=''><mtable><mtr><mtd><msub><mi>I</mi><mi>x</mi></msub><mo>=</mo><msub><mi>j</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>x</mi></msub><mo>+</mo><msub><mi>i</mi><mi>x</mi></msub></mtd></mtr><mtr><mtd><msub><mi>I</mi><mi>y</mi></msub><mo>=</mo><msub><mi>j</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub></mtd></mtr><mtr><mtd><msub><mi>I</mi><mi>z</mi></msub><mo>=</mo><msub><mi>j</mi><mi>z</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr></mtable></mfenced><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>9</mn><mo>)</mo></mrow></mrow></math>]]></maths>其中,j<sub>x</sub>,j<sub>y</sub>,j<sub>z</sub>为边长与空间步长相等的立方体网格Δα<sup>3</sup>所在的工作组对应的空间位置;n<sub>x</sub>,n<sub>y</sub>,n<sub>z</sub>为工作组沿三维的网格数;i<sub>x</sub>,i<sub>y</sub>,i<sub>z</sub>为立方体网格Δα<sup>3</sup>在工作组内部所对应的具体位置坐标;步骤4-5-3-2:通过式(10)确定全局存储空间的位置坐标代号i000、i100、i010与i001:<maths num="0009"><![CDATA[<math><mrow><mfenced open='{' close=''><mtable><mtr><mtd><mi>i</mi><mn>000</mn><mo>=</mo><msub><mi>I</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>i</mi><mn>100</mn><mo>=</mo><mrow><mo>(</mo><msub><mi>I</mi><mi>x</mi></msub><mo>-</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>i</mi><mn>010</mn><mo>=</mo><msub><mi>I</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><mrow><mo>(</mo><msub><mi>I</mi><mi>y</mi></msub><mo>-</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>i</mi><mn>001</mn><mo>=</mo><msub><mi>I</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>N</mi><mi>z</mi></msub><mo>/</mo><mn>4</mn><mo>+</mo><msub><mi>I</mi><mi>z</mi></msub><mo>-</mo><mn>1</mn></mtd></mtr></mtable></mfenced><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>10</mn><mo>)</mo></mrow></mrow></math>]]></maths>N<sub>y</sub>和N<sub>z</sub>为整个FDTD仿真空间Y轴和Z轴方向所对应的网格;通过式(11)确定本地存储空间的位置坐标代号localindex、local100、local010和local001:<maths num="0010"><![CDATA[<math><mrow><mfenced open='{' close=''><mtable><mtr><mtd><mi>localindex</mi><mo>=</mo><msub><mi>i</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>local</mi><mn>100</mn><mo>=</mo><mrow><mo>(</mo><msub><mi>i</mi><mi>x</mi></msub><mo>-</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>local</mi><mn>010</mn><mo>=</mo><msub><mi>i</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><mrow><mo>(</mo><msub><mi>i</mi><mi>y</mi></msub><mo>-</mo><mn>1</mn><mo>)</mo></mrow><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub></mtd></mtr><mtr><mtd><mi>local</mi><mn>001</mn><mo>=</mo><msub><mi>i</mi><mi>x</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>y</mi></msub><mo>&times;</mo><msub><mi>n</mi><mi>z</mi></msub><mo>+</mo><msub><mi>i</mi><mi>z</mi></msub><mo>-</mo><mn>1</mn></mtd></mtr></mtable></mfenced><mo>-</mo><mo>-</mo><mo>-</mo><mrow><mo>(</mo><mn>11</mn><mo>)</mo></mrow></mrow></math>]]></maths>步骤4-5-3-3:将GPU全局存储空间的电磁场数据及相关的三维临时电磁参量传递到本地存储空间;步骤4-5-3-4:将三维电场空间位置坐标的循环迭代转化为基于OpenCL的并行计算;(1)y轴方向H<sub>x</sub>和H<sub>z</sub>数据转化过程:首先判断该网格处的坐标I<sub>y</sub>是否大于全局存储空间Y轴坐标下限0,若否,则将H<sub>x-010</sub>和H<sub>z-010</sub>都设置为float4[1.0,1.0,1.0,1.0];若是,则进一步判断本地存储空间的网格坐标i<sub>y</sub>是否大于本地存储空间y轴纵坐标下限0,若否,则将H<sub>x-010</sub>和H<sub>z-010</sub>分别设置为H<sub>x</sub>[i010]和H<sub>z</sub>[i010],若是,则将H<sub>x-010</sub>和H<sub>z-010</sub>分别设置为H<sub>x-l</sub>[local010]和H<sub>z-l</sub>[local010];其中,H<sub>x-010</sub>和H<sub>z-010</sub>的下角标010表示磁场数据在y轴方向前移一位;(2)z轴方向H<sub>x</sub>和H<sub>y</sub>数据转化过程:首先判断该网格处的纵坐标I<sub>z</sub>是否大于全局存储空间z轴坐标下限0,若否,则将H<sub>x-001</sub>设置为:float4(1.0f,H<sub>x-l</sub>[localindex].x,H<sub>x-l</sub>[localindex].y,H<sub>x-l</sub>[localindex].z),将H<sub>y-001</sub>设置为:float4(1.0f,H<sub>y-l</sub>[localindex].x,H<sub>y-l</sub>[localindex].y,H<sub>y-l</sub>[localindex].z);若是,进一步判断本地存储空间的网格坐标i<sub>z</sub>是否大于本地存储空间z轴坐标下限0,若否,则将H<sub>x-001</sub>设置为float4(H<sub>x-l</sub>[i001].w,H<sub>x-l</sub>[localindex].x,H<sub>x-l</sub>[localindex].y,H<sub>x-l</sub>[localindex].z),将H<sub>y-001</sub>设置为float4(H<sub>y-l</sub>[i001].w,H<sub>y-l</sub>[localindex].x,H<sub>y-l</sub>[localindex].y,H<sub>y-l</sub>[localindex].z),若是,设置H<sub>x-001</sub>为float4(H<sub>x-l</sub>[local001].w,H<sub>x-l</sub>[localindex].x,H<sub>x-l</sub>[localindex].y,H<sub>x-l</sub>[localindex].z),置H<sub>y-001</sub>为float4(H<sub>y-l</sub>[local001].w,H<sub>y-l</sub>[localindex].x,H<sub>y-l</sub>[localindex].y,H<sub>y-l</sub>[localindex].z);其中H<sub>x-001</sub>和H<sub>y-001</sub>的下角标001表示磁场数据在z轴方向前移一位,.x、.y、z和.w依次表示float4型数据中4个float型数据;(3)x轴方向H<sub>y</sub>和H<sub>z</sub>数据转化过程:首先判断该网格处的坐标I<sub>x</sub>是否大于全局存储空间x轴坐标下限0,若否,则将H<sub>y-100</sub>和H<sub>z-100</sub>都设置为float4[1.0,1.0,1.0,1.0];若是,则进一步判断本地存储空间的网格坐标i<sub>x</sub>是否大于本地存储空间x轴纵坐标下限0,若否,则将H<sub>y-100</sub>和H<sub>z-100</sub>分别设置为H<sub>y</sub>[i100]和H<sub>z</sub>[i100],若是,则将H<sub>y-100</sub>和H<sub>z-100</sub>分别设置为H<sub>y-l</sub>[local100]和H<sub>z-l</sub>[local100];其中,H<sub>y-100</sub>和H<sub>z-100</sub>的下角标100表示磁场数据在x轴方向前移一位;步骤4-5-3-5:确定x方向的电场E<sub>x</sub>、y方向的电场E<sub>y</sub>与z方向的电场E<sub>z</sub>;步骤4-5-4:如果需要对仿真后的电场数据进行存储,则利用OpenCL标准库函数clEnqueueReadBuffer()将电场E<sub>x</sub>、E<sub>y</sub>、E<sub>z</sub>由GPU显存传递到CPU内存,以便于在内存中对电场数据进行后处理;步骤4-6:保存所需要的电磁场数据:保存时间步n<sub>0</sub>下的空间电磁场数据,以及保存所关心的位置点的电磁场在时间步n<sub>1</sub>~n<sub>2</sub>下的电磁场随时间变化情况的数据;步骤5:释放显存中存储的数据;步骤6:仿真完成后,释放CPU内存资源;其中,OpenCL表示开放计算语言,GPU表示图形处理器,FDTD表示时域有限差分。
地址 100830 北京市西城区月坛北小街2号