下表列出了此版本 VisualApplets 所有受支持硬件平台的重要硬件详细信息。有关详细列表,请查阅各个产品的技术参数表。
| 资源 | imaFlex CXP-12 Quad | imaFlex CXP-12 Penta | imaFlex 2 Dual 100 | ||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Vision Processor | Xilinx UltraScale+ XCKU3P-FFVD900-1-E | Xilinx UltraScale+ XCKU3P-FFVB676-1-E | Xilinx UltraScale+ XCKU15P-FFVE1517-1-E | ||||||||||
| 查找表 (LUT) | 160679 | 161049 | 447992 | ||||||||||
| 触发器 | 323224 | 323216 | 895984 | ||||||||||
| Block RAM (18k) | 720 | 720 | 1776 | ||||||||||
| URAM Blocks (288k) | 48 | 48 | 128 | ||||||||||
| 嵌入式算术逻辑单元 (DSP48) | 1368 | 1368 | 1800 | ||||||||||
| RAM 大小 | 3 x 512 MiB DDR4 | 5 x 512 MiB DDR4 | 2 @ 5 x 1024 MiB DDR4 | ||||||||||
| RAM 数据宽度 | 384 Bit | 640 Bit | 640 Bit | ||||||||||
| RAM 总带宽(共享) | 14.4 GB/![]() |
24.0 GB/s![]() |
2 @ 24.0 GB/s![]() |
||||||||||
| 基础设计时钟(默认) | 312.5 MHz![]() |
312.5 MHz![]() |
391.5 MHz![]() |
||||||||||
| 基础设计时钟(最大) | 400.0 MHz | 400.0 MHz | 420.0 MHz | ||||||||||
| 主机接口 | PCIe x 8 Gen 3(直接内存访问) | PCIe x 8 Gen 3(直接内存访问) | PCIe x 16 Gen 3(直接内存访问) | ||||||||||
| 主机接口(PCIe x 8 Gen 3)带宽(理论值) | 8000 MB/s | 8000 MB/s | 16000 MB/s | ||||||||||
| 主机接口(PCIe x 8 Gen 3)带宽(典型值/最大值) | 7200 MB/s 持续数据带宽 | 7200 MB/s 持续数据带宽 | 13000 MB/s 持续数据带宽![]() |
||||||||||
|
|||||||||||||
表 68. imaFlex 平台硬件配置
| 资源 | mE5 marathon VCX-QP | mE5 marathon VCL | mE5 marathon VCLx | ||||
|---|---|---|---|---|---|---|---|
| Vision Processor | Xilinx Kintex7 XC7K160T - 2FFG676C FPGA | Xilinx Kintex7 XC7K160T - 1FBG676C FPGA | Xilinx Kintex7 XC7K410T - 1FBG676C FPGA | ||||
| 查找表 (LUT) | 101400 | 101400 | 254200 | ||||
| 触发器 | 202800 | 202800 | 508400 | ||||
| Block RAM (18k) | 650 | 650 | 1590 | ||||
| 嵌入式算术逻辑单元 (DSP48) | 600 | 600 | 1540 | ||||
| RAM 大小 | 4 x 512MiB DDR3 | 4 x 512MiB DDR3 | 4 x 512MiB DDR3 | ||||
| RAM 数据宽度 | 512 Bit | 256 Bit | 256 Bit | ||||
| RAM 总带宽(共享) | 12.8 GB/s![]() |
6.4 GB/s![]() |
6.4 GB/s![]() |
||||
| 基础设计时钟(默认) | 125MHz | 125MHz | 125MHz | ||||
| 基础设计时钟(最大) | 312.5 MHz![]() |
312.5 MHz![]() |
312.5 MHz![]() |
||||
| 主机接口 | PCIe x 4 Gen 2 (Direct Memory Access) | PCIe x 4 Gen 2 (Direct Memory Access) | PCIe x 4 Gen 2 (Direct Memory Access) | ||||
| Host Interface (PCIe x 4 Gen 2) Bandwidth (theor.) | 1x2000 MB/s | 1x2000 MB/s | 1x2000 MB/s | ||||
| Host Interface (PCIe x 4 Gen 2) Bandwidth (typ./max.) | 最高 1800 MB/s 的持续数据带宽 | 高达 1800 MB/s 的持续数据带宽 | 高达 1800 MB/s 的持续数据带宽 | ||||
|
|
|||||||
表 69. microEnable 5 marathon 硬件配置
每个硬件平台上的设备资源都是有限的。以下列表显示了 所有支持平台可用的资源。Operator 会消耗设备资源,并且 大多数资源实例只能使用一次。此规则有一些例外情况, 例如 GPI operator。在这些情况下,资源消耗情况记录在 operator 参考文档中。
设备资源的分配方式为
-
自动分配,
-
使用 operator parameters 分配,或
-
在 Resources 对话框中分配。
有关更多信息,请参阅 'Allocation of Device Resources'。
| 资源 | imaFlex 2 Dual 100 | ||||||||
|---|---|---|---|---|---|---|---|---|---|
Port[0] CoF Lane![]() |
4 | ||||||||
Port[1] CoF Lane![]() |
4 | ||||||||
Port[0] CoF RX Trigger Lane![]() |
4 | ||||||||
Port[1] CoF RX Trigger Lane![]() |
4 | ||||||||
Port[0] CoF TX Trigger Lane![]() |
4 | ||||||||
Port[1] CoF TX Trigger Lane![]() |
4 | ||||||||
Port[0] CoF Status Lane![]() |
4 | ||||||||
Port[1] CoF Status Lane![]() |
4 | ||||||||
Port[0] DF RX Data Lane![]() |
4 | ||||||||
Port[1] DF RX Data Lane![]() |
4 | ||||||||
Port[0] DF RX Meta Lane![]() |
4 | ||||||||
Port[1] DF RX Meta Lane![]() |
4 | ||||||||
Port[0] DF TX Data Lane![]() |
4 | ||||||||
Port[1] DF TX Data Lane![]() |
4 | ||||||||
Port[0] DF TX Meta Lane![]() |
4 | ||||||||
Port[1] DF TX Meta Lane![]() |
4 | ||||||||
Port[0] DF Green LED Lane![]() |
4 | ||||||||
Port[0] DF Red LED Lane![]() |
4 | ||||||||
Port[1] DF Green LED![]() |
1 | ||||||||
Port[1] DF Red LED![]() |
1 | ||||||||
DmaToHostPort![]() |
5 | ||||||||
DmaFromHostPort![]() |
1 | ||||||||
GPI![]() |
16 | ||||||||
GPO![]() |
16 | ||||||||
EventPort![]() |
31 | ||||||||
EventID![]() |
64 | ||||||||
User LED![]() |
6 | ||||||||
ImageChannel![]() |
1024 | ||||||||
RAM![]() |
2 @ 从 1 x 5 GiB 到 8 x 625 MiB | ||||||||
|
|||||||||
表 70. imaFlex 2 Dual 100 设备资源列表
| 资源 | imaFlex CXP-12 Quad | imaFlex CXP-12 Penta | ||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| 相机端口 | 4 | 5 | ||||||||||||
| CxpStatusPort | 4 | 5 | ||||||||||||
| CxpRxTriggerPort | 4 | 5 | ||||||||||||
| CxpTxTriggerPort | 4 | 5 | ||||||||||||
| DMA | 4 | 5 | ||||||||||||
| DmaFromHostPort | 1 | 1 | ||||||||||||
GPO![]() |
10 OUT | 12 OUT | ||||||||||||
GPI![]() |
12 IN | 12 IN | ||||||||||||
LED Ports![]() |
6 | 6 | ||||||||||||
SignalChannel![]() |
4000 | 4000 | ||||||||||||
EventPort![]() |
32 | 32 | ||||||||||||
EventID![]() |
64 | 64 | ||||||||||||
ImageChannel![]() |
1024 | 1024 | ||||||||||||
RAM![]() |
从 1 x 1.5 GiB 到 8 x 192 MiB | 从 1 x 2.5 GiB 到 8 x 320 MiB | ||||||||||||
|
||||||||||||||
表 71. imaFlex CXP-12 Quad 和 imaFlex CXP-12 Penta 的设备资源列表
表 72. microEnable 5 marathon 的设备资源列表
imaFlex 2 Dual 100 平台包含两个独立的物理 RAM 库,每库容量为 5 GiB。根据 applet 中使用的基于 RAM 的 VisualApplets 算子的数量,这些物理库可根据需要划分为不重叠的 memory 区域。在 VisualApplets 中,这些区域显示为虚拟 RAM 库。当算子需要 RAM 时,它会预留一个虚拟 RAM 库,该库对应于物理 RAM 中的一个专用、不重叠的区域。
有关 VisualApplets memory 算子的实用指导,请参阅 Memory Elements 教程主题。
在 imaFlex 2 Dual 100 平台上,每个物理 RAM 库最多可定义 8 个不重叠的 memory 区域,这意味着两个 RAM 接口总共有 16 个区域。如果仅将一个 RAM 算子分配给物理接口,则该算子可以访问该接口的全部 5 GiB 容量。当多个算子共享同一个物理接口时,可用 memory 将在它们之间按比例分配。例如,如果将 8 个算子分配给同一接口,则每个算子获得 5 GiB memory 的 1/8,即每个算子约获得 0.625 GiB。
imaFlex 2 Dual 100 上的 RAM 带宽在连接到同一物理接口的所有算子之间平均分配;它不专属于任何单个算子。
-
如果某个设计在一个接口上使用了全部 8 个 RAM 资源,则每个基于 RAM 的算子将获得总接口带宽的大约 1/8(根据算子的效率因数进行调整)。
-
如果仅使用一个基于 RAM 的算子,则该算子可以使用该接口的全部最大带宽。
-
如果两个算子共享同一个接口,则每个算子将获得总带宽的一半,以此类推。
平台的 2 个物理 RAM 接口在 VisualApplets 中映射为 16 个虚拟 RAM 端口。第一个 RAM 接口映射到 RAM 资源索引 0 到 7,第二个映射到 RAM 资源索引 8 到 15。
未分配(因此未被使用)的 RAM 端口始终获得 0% 的 memory 容量。这意味着总可用 memory 仅在积极使用 RAM 端口的运算符之间进行分配。
-
如果仅使用 1 个端口:该端口获得 100% 的可用 memory。
-
如果使用 2 个端口:每个端口获得 50% 的可用 memory。
-
如果使用 3 个端口:资源 ID 最小的端口获得 50%,其余 2 个端口各获得 25%。
-
如果使用 4 个端口:所有 4 个端口各获得 25%。
-
如果使用 5 个端口:前 3 个端口(具有最小的资源 ID)各获得 25%,其余 2 个端口各获得 12.5%。
-
如果使用 6 个端口:资源 ID 最小的 2 个端口各获得 25%,其余 4 个端口各获得 12.5%。
-
如果使用 7 个端口:资源 ID 最小的端口获得 25%,其余 6 个端口各获得 12.5%。
-
如果使用 8 个端口:所有端口各获得 12.5%。
![]() |
不对称 Memory 分配 |
|---|---|
|
在进行不对称大小划分时,同一物理组内具有最低 RAM 索引的端口将获得更大的分配。例如,如果使用 3 个 RAM 端口(0、1 和 2),端口 0 获得 50% 的 RAM 大小,而端口 1 和 2 各获得 25%。如果端口为 8、9 和 10,情况也是如此,因为它们映射到第二个 RAM 接口,但仍属于同一物理 RAM 组。 |
RAM 索引不需要是连续的;它们的绝对顺序决定了分配。RAM 索引是一个虚拟标识符,不会影响 FPGA 资源使用,即使序列中存在间隙也是如此。例如,如果使用 3 个 RAM 端口(1、5 和 7):端口 1 获得 50% 的 RAM 大小,端口 5 和 7 各获得 25%。
当所有资源都映射到同一物理组时,RAM 索引的分配方式没有优劣之分。如果特定的设计运算符需要比其他运算符更多的 RAM,您可以使用 VisualApplets 提供的自动分配,或进行手动调整。
![]() |
独立的 RAM 接口 |
|---|---|
|
两个物理 RAM 接口是完全独立的。例如,如果使用两个运算符,并且一个分配给第一个 RAM 接口,另一个分配给第二个 RAM 接口,则每个运算符都可以利用其各自接口的完整最大 RAM 大小。 |
共享 memory 控制器使用轮询(Round-robin)算法在物理 RAM 接口内的所有已分配端口之间均匀分配带宽。该算法基于基于信用的仲裁方案。当端口变为活动状态时,只要它继续提供新的 RAM 作业,它就会在设定的信用时钟周期数内保持活动状态。如果活动端口没有更多作业,它将被停用,并且激活令牌将移动到下一个有挂起请求的端口。这可确保带宽永远不会浪费在空闲端口上。
信用值由固件在小程序(applet)综合期间根据所使用的 RAM 运算符的数量进行编程。它们无法在运行时或通过 Framegrabber SDK 进行更改。用户无权访问信用配置。
当端口处于活动状态时,它拥有 memory 控制器 100% 的带宽。如果物理组中的所有 8 个端口都均匀处于活动状态,则每个端口随着时间的推移大约获得总带宽的 1/8。在其他情况下,实际平均带宽取决于每个端口的负载。
物理 RAM 接口完全独立。将基于 RAM 的运算符分配给不同的接口可最大化带宽效率。带宽仅在连接到同一物理 RAM 接口的运算符之间共享。
平台 imaFlex CXP-12 Quad 和 imaFlex CXP-12 Penta 仅组装有一个物理 RAM 组(其大小因平台而异)。根据小程序内部使用的基于 RAM 的 VisualApplets 运算符的数量,这个单一的物理组被动态格式化为非重叠区域。这些区域在 VisualApplets 内部表示为虚拟 RAM 组。当运算符保留 RAM 资源时,它使用的是映射到物理 RAM 内独占非重叠 memory 区域的虚拟 RAM 组。imaFlex 平台上最多可以定义 8 个非重叠区域。当仅使用 1 个 RAM 运算符时,该运算符获得平台的完整 RAM 大小。每个附加运算符分配的大小会根据对接在同一物理接口上的运算符数量成比例地减少该运算符拥有的尺寸。如果使用 8 个运算符,每个运算符将分配平台 memory 大小的 1/8。
但是,RAM 带宽在设计中的所有基于 RAM 的运算符之间共享。当设计利用所有 8 个 RAM 资源时,8 个基于 RAM 的运算符中的每一个都可以具有高达 1/8 GB/s 的独占带宽,减去该特定运算符的效率系数。当设计中仅使用一个基于 RAM 的运算符时,该运算符将获得平台的总带宽。当使用 2 个运算符时,两个运算符各获得总带宽的一半,依此类推。
未分配且因此未使用的 RAM 端口始终获得 0% 的 memory 大小。
-
使用 1 个端口:使用的端口获得 100%。
-
使用了 2 个端口:两个使用的端口各获得 50%。
-
使用了 3 个端口:资源 ID 编号最小的端口获得 50%,另外 2 个使用的端口各获得 25%。
-
使用了 4 个端口:全部 4 个端口各获得 25%。
-
使用了 5 个端口:资源 ID 编号最小的 3 个端口各获得 25%。最后 2 个端口各获得 12.5%。
-
使用了 6 个端口:资源 ID 编号最小的 2 个端口各获得 25%。另外 4 个端口各获得 12.5%。
-
使用了 7 个端口:资源 ID 编号最小的端口获得 25%。另外 6 个端口各获得 12.5%。
-
使用了 8 个端口:所有端口各获得 12.5%。
![]() |
|
|
在采用非对称大小分区的情况下,具有较小 RAM 索引的端口将获得更大的分配份额。例如,使用了 3 个 RAM 端口:0、1、2。端口 0 获得 50% 的 RAM 大小分配,端口 1 和端口 2 则各获得 25%。 RAM 索引无需连续,其绝对顺序决定了分配。当排序中存在间隙时,RAM 索引是一个虚拟编号,对 FPGA 资源使用没有任何影响。例如,使用了 3 个 RAM 端口:1、5、7。端口 1 获得 50% 的 RAM 大小分配,端口 5 和端口 7 则各获得 25%。 分配算子的 RAM 索引既没有优势也没有劣势。可以使用 VisualApplets 自动分配,或者在某个特殊设计算子需要比其他算子更多的 RAM 大小手动进行调整。 |
共享 Memory 控制器应用 Round-robin 算法,将带宽均匀分布在所有已分配的端口上。该算法使用信用仲裁机制:当端口处于活动状态时,只要该端口持续提供新的 RAM 作业,它就可以保持活动状态,持续时间为信用的时钟周期。一旦某个端口被激活但没有更多作业,该端口就会被停用,激活令牌将跳转到排队中的下一个有等待请求作业的端口。通过这种方式,带宽绝不会浪费在空闲上。信用仅在小程序合成期间由固件根据所使用的 RAM 算子数量专门进行编程,无法在 Framegrabber SDK 中或运行期间进行更改。用户无法访问信用的编程。当活动端口拥有 RAM 接口时,它将访问 Memory 控制器的 100% 带宽。当所有 8 个端口均被使用且均匀处于活动状态时,随着时间推移,每个端口的最终带宽为 1/8。在所有其他情况下,端口上的负载决定了每个端口的实际平均带宽。
microEnable 5 marathon 平台仅组装了一个物理 RAM 库(其大小因平台而异)。这个单一的物理库被格式化为 4 个不重叠的 memory 区域。这 4 个区域在 VisualApplets 内部表示为 4 个虚拟 RAM 库。当算子保留 RAM 资源时,它使用的是映射到物理 RAM 内部排他性不重叠 memory 区域的虚拟 RAM 库。
然而,RAM 带宽在设计中的所有基于 RAM 的算子之间共享。当设计利用所有 4 个 RAM 资源时,4 个基于 RAM 的算子中的每一个都可以拥有高达 1.6 GB/s 的独占带宽,减去该特定算子的效率系数。当设计中仅使用一个基于 RAM 的算子时,该算子将获得 6.4 GB/s 的总带宽。当使用 2 个算子时,两个算子各获得总带宽的一半,依此类推。
![]() |
每个算子的带宽 |
|---|---|
|
板载 RAM 提供 6.4 GB/s 的总带宽。单个基于 RAM 的算子可用的带宽是总带宽除以设计中所有已实例化基于 RAM 的算子的数量。 |
在使用基于 RAM 的算子进行设计时,需要考虑此 RAM 架构。
由于共享带宽架构,在使用多个基于 RAM 的算子时,小程序开发人员应利用算子的 memory 接口(RAM Data Width)的所有 256 位,以通过 memory 接口实现最大吞吐量,即使单个 RAM 算在其输入端需要的带宽较少也是如此。
imaFlex 2 Dual 100 提供 2 个光纤 QSFP28 连接器:C0 和 C1。
两个连接器均支持 CoF(CXP over Fiber)和数据转发协议。每个光纤连接器都有自己的 LED:四个 LED 分配给连接器 C0,一个 LED 分配给连接器 C1。
每个连接器均支持 QSFP28 光模块。QSFP28 接口在两个方向上提供 4 个光纤连接,即 4 个 RX 和 4 个 TX 连接。在算子文档中,光纤连接被称为 lane。每个 QSFP28 端口在 RX 和 TX 方向上都有 4 个光纤 lane,标记为 0 到 3。每个 lane 的运行速度为 25 Gbit/s。因此,单个 QSFP28 连接器可以在 TX 和 RX 方向传输 100 Gbit/s 的累积带宽。
imaFlex 2 Dual 100 提供数据转发功能,能够跨多个采集卡双向传输数据。VisualApplets 中的数据转发支持各种拓扑结构来传输数据和元数据,包括菊花链以及更高级的模式。数据转发行为由用户通过 VisualApplets 算子完全控制。相机数据、applet 生成的数据和元数据可以在 TX 和 RX 方向上独立传输。VisualApplets 还可对通道进行多路复用,允许通过两个独立的虚拟通道在单个光纤通道上同时发送元数据和常规图像数据。元数据享有优先权,以确保及时交付。
由于光纤技术支持双向通信,高级的主从应用程序可以允许主设备控制从设备接收哪些数据并收集其处理结果。在从属 GPU 或 CPU 上生成的处理结果可以通过 DmaFromPC 传回,然后通过数据转发数据算子转发回主采集卡。
在典型的数据转发菊花链配置中,选定的相机数据被转发到多个采集卡。然后,这些采集卡以极低的延迟通过 PCIe 将数据传输到外部 GPU。
CoF (CXP over Fiber) 使用四个下行连接和一个上行连接。两个采集卡之间的数据转发链路配置为仅传输所需的数据;它们不传输原生的 CoF 流量,而是承载 VisualApplets 数据和元数据流。CoF 和数据转发均受前向纠错 (FEC) 保护。
主采集卡连接到相机并将选定的数据部分转发给下一个从采集卡。每个从采集卡提取其自身处理所需的数据,并将图像流中其余未处理的部分转发给序列中的下一个从采集卡。链中的最后一个采集卡充当终点,不再进一步转发任何数据。
上面的示例是菊花链拓扑的简化表示。在更高级的配置中,两个连接的采集卡可以自由交换数据:它们可以在彼此之间跨越 1、2、3 或 4 通道连接。RX 和 TX 方向可以使用不同数量的通道。
多个光学通道可以组合成虚拟通道,从而允许通过单个 QSFP28 连接器传输多个数据通道。除了图像数据传输外,VisualApplets 还为每个光学通道提供专用的元通道。该元通道优先于普通图像数据,并且以极低的抖动和延迟进行传输,从而使应用程序能够实现时间戳和板间同步。小型边带信息也可以通过元通道传输,例如用于配置光纤连接另一端的从属伙伴。伙伴可以通过自己的元通道将控制和状态信息返回给主设备。每个采集卡还可以向其伙伴发送处理后的图像数据,聚合带宽最高可达 100 Gb/s。
在单个 QSFP28 接口上,两个采集卡之间最多可以跨越四个元通道(在 TX 和 RX 方向上独立)。每个元通道运行速率为 25 Gb/s。图像数据通道可以跨越 1、2、3 或 4 个光学通道以形成虚拟数据传输通道。
QSFP28 数据转发接口允许以下虚拟数据通道组合:
-
1 x4 通道:100 Gbit/s
-
运行速率为 75 Gbit/s 的 1 x3 通道和运行速率为 25 Gbit/s 的 1 x1 通道
-
运行速率各为 50 Gbit/s 的 2 x2 通道
-
运行速率为 50 Gbit/s 的 1 x2 通道和运行速率为 25 Gbit/s 的 2 x1 通道
-
运行速率各为 25 Gbit/s 的 4 x1 通道
RX 和 TX 端完全独立运行。这意味着可以根据需要实现或省略反向 (RX) 方向。如果实现了该方向,它不必与正向 (TX) 方向对称。
元通道和数据通道独立运行。每个元通道精确使用一个光纤通道,运行速率为 25 Gb/s。元通道专为传输少量数据而设计。由于它们具有优先权,元通道传输会暂时暂停同一光纤通道上的常规数据传输。
为了支持数据转发功能,VisualApplets 提供了以下算子:
Basler 作为 VisualApplets 设计提供数据转发示例,并附带 C++ SDK 控制应用程序。在这些示例中,您可以了解如何使用这些算子进行数据转发。这些示例作为 VisualApplets 示例提供,位于 Examples/Acquisition/DataForwarding。您可以在以下位置找到有关这些数据转发示例的文档: “Data Forwarding for CoaXPress over Fiber Frame Grabber” 主题,位于 基础知识与示例.
在某些限制条件下,可以构建更复杂的相机-采集卡模型。两个采集卡之间的光学传输具有极低的延迟:数据字从一个采集卡传输到另一个采集卡大约只需 120 ns。
菊花链拓扑是将处理负载分配到多个 CPU/GPU 集群中最常见的方法:
主采集卡连接到相机;第二个 QSFP28 端口连接到下一个从机。每个从机处理一部分传入的数据,并将剩余的数据转发给下一个设备。链中的最后一个采集卡充当端点。除最后一个采集卡外,所有采集卡都使用两个 QSFP28 端口。
对于某些应用,可以将两个 100 Gb/s 相机连接到单个采集卡。这要求相机不是以最大带宽运行,或者可以在 VisualApplets 中进行预处理,然后再将数据存储在 RAM 中,从而稍微降低带宽,使两个相机流都能容纳在两个 RAM 接口中。在这种配置下,采集卡必须在 VisualApplets 中执行额外的处理,以降低产生的数据速率,使其与约 13 GB/s 的有限 PCIe 吞吐量相匹配。
在这种情况下,每个采集卡连接到其自己的相机。第二个 QSFP28 端口用于采集卡之间的通信,支持双向高达 100 Gbit/s 的数据交换,用于执行复杂的计算任务和同步。







![[注意]](../common/images/admon/note.png)












上一页

