IOs interface memory secutity

使用自定义 RISC-V ISA 指令创建特定域的处理器

发布时间:2020-11-20 点击数:

1、介绍


当系统芯片(SoC)开发人员在设计中包括处理器时,他们在解决计算难题时面临着多种选择.复杂的 SoC 通常具有各种处理器内核,这些处理器内核负责各种功能,如运行主应用程序、通信、信号处理、安全性和管理存储。迄今为止,传统上,这些内核可分为不同的类别,如:微控制器 (MCU)、数字信号处理器(DSP)、图形处理器(GPU)和应用程序处理器。此外,还为非常专业的应用程序开发了一些独特的体系结构和指令集。然而,独特指令集的缺点是缺乏软件生态系统。


今天,经典内核类别之间的区别日渐模糊。这是因为,如果内核设计的方式正确,该处理器可能涵盖多个用法。此外,通过创建适应 SoC 需求的处理器,可以提高面积和功率方面的硅效率。


创建特定域处理器的最新催化剂是RISC-V ISA(指令系统体系结构)。由于 ISA 的使用是开放的,免版税,因此它作为实现处理器设计的基础,很有吸引力。此外,每个字长的基本指令集的存在意味着可将使用基本指令集的软件移植到具有该字长的所有 RISC-V 处理器。


RISC-V ISA 采用模块化方式设计,这意味着 ISA 具有几组可根据需要启用或禁用的指令(ISA 扩展)。这可以精确实现此域所需的指令组,而不必为未使用的面积或电源付费。


其中一组很特殊;它没有标准的预定义指令。设计人员可以对需加速的应用程序添加所需的任何指令。这是一个强大的功能,因为它不会破坏任何软件兼容性,并同时为发明和差异化留下了空间。本白皮书介绍了如何添加特定域的指令(自定义 ISA 扩展)、如何在 SDK 中构建所有所需的工具,以及如何在 HDL (例如 Verilog)中实现自定义 ISA 扩展。最终结果是一个经优化的特定域处理器。


2、RISC-V 指令系统体系结构


RISC-V ISA 被组织成指令组(基本 ISA 和扩展)。您可以将其随意混合和匹配。例如,您可能具有实现绝对最小值的 RISC-V 处理器,或者具有实现所有 ISA 扩展的 RISC-V 处理器,具体取决于设计需求。


下表列出了 RISC-V 基金会已批准的主要 ISA 扩展和目前正在开发的主 ISA 扩展。


chapter_2_table_ISA扩展.png

随着新增更多 ISA 扩展,上表将进行扩展。


尽管该表已经很广泛,但当没有符合设计需求且现成合适的 ISA 扩展时,可能会出现这种情况。在这种情况下,RISC-V 规范允许添加自定义 ISA 扩展。这可能是该公司的"秘密武器"和关键不同点。由于 RISC-V 生态系统的性质,自定义 ISA扩展不会违反主要参数——即使使用其他指令,您的处理器仍完全符合 RISC-V 标准,并且可以运行从该生态系统中取得的通用软件堆栈。


图 1显示了自定义 ISA 扩展如何适合软件堆栈。在最低级别上,有一个具有自定义 ISA 扩展且符合 RISC-V 规格的处理器。它运行一个操作系统,无论是实时操作系统 (RTOS) 还是传统操作系统。它可利用兼容标准 RISC-V 处理器的任何编译器编译(无特殊的 ISA 扩展)。除了操作系统,还有三个应用程序。 App1 是一个不需要任何加速的通用应用程序。您可以使用公开可用的现成编译器(例如 GCC)来编译它,或者甚至可以使用预编译的应用程序;无论哪种方式, RISC-V 处理器都能运行它。 App2 和App3是需要尽可能快速运行的重要应用程序。这些应用程序必须使用专门了解自定义 ISA 扩展的编译器进行编译。该编译器可以利用可加速App2和App3的新指令。.


chapter_2_schema_图1.png


图2显示了一个具有自定义 ISA 扩展且符合 RISC-V 规格的处理器示例。App1 不使用自定义 ISA 扩展。App2 和 App3 使用通用 API。该API由了解自定义 ISA 扩展的库执行,App2 和 App3可以因此再次获得加速。App2 和 App3 都可以在现成的RISC-V 处理器中重复使用。接下来只需执行所需 API 的库。在此系统中,使用自定义ISA 扩展从 RISC-V将App2  和 App3移到没有扩展的 RISC   V非常简单,并且不需要任何应用程序移植。


chapter_2_schema_图2.png


在以下各部分,我们将更详细地介绍自定义 ISA 扩展以及Codasip 如何在设计和验证方面提供帮助。


3、自定义指令集扩展


自定义指令集体系结构或自定义 ISA 扩展屡见不鲜,已得到广泛应用。然而,他们通常需要付出很多努力。首先,您需要确定改进处理器设计的指令。然后,您需要将它们添加到 C 编译器、模拟器、调试器和其他工具中,并验证这些更改是否将相同的内容添加到所有这些不同的工具中。添加自定义指令通常需要一些手动操作。通常,为了便于编程工具可以传递和编译这些指令,您需要一个团队将新指令添加到 SDK 中。您还需要向指令集模拟器添加新代码。最后,必须扩展 RTL,并且必须验证对 RTL 的任何更改。根据手动工作量的不同,ISA 扩展在时间和资源方面可能相当昂贵。


为了降低 ISA 扩展的成本,需要尽可能多地自动化工作 work,从确定合适的指令到 RTL 验证。这正是Codasip的功能优势所在。Codasip 提供了一个名为 Studio 的 EDA 工具,使您能够自定义 Codasip 提供的现成处理器。您可以通过 Codasip的现成 RISC-V 兼容处理器开始工作,只需根据需要添加自定义 ISA 扩展,也可以从头开始编写自己的 RISC-V 处理器。


自定义指令可以很简单,例如乘加单元(multiple-and-accumulate)的变体,也可以是自定义控制指令,如零开销循环(硬件循环)。您还可以拥有具有后增量或前增量的特殊负载/存储指令。这说明自定义指令因复杂性而不同,会影响 C 编译器的功能和由此产生的处理器的性能。C 编译器可以使用简单的指令,而无需更改原始 C 代码。换句话说,你可以有一个应用程序,你可以将其编译成x86或RISC-V。如果指令过于复杂,则使用它的唯一方法就是内联汇编或 C 内嵌函数。限制约为 ~25次操作和 ~3次输出。另一方面,更复杂的指令通常会提高性能,因此结果值得付出此类努力。


有一种将内联汇编或内嵌集成到库中的简单方法。该库也采用一种通用实现方式。这种库的好处是,您可以实现最终应用,并且您可以为多个目标对其进行编译。每个目标可能使用不同的实现方式。该应用不需要了解最终实现。


下面的示例显示了此类库的一个代码段。它表示一个简单的字节交换函数。如果存在指定的宏,C 编译器具有执行交换的特殊指令。否则,将采用标准方法。


// universal byteswap() function

inline uint32_t byteswap(const uint32_t word) {

#ifdef ISA_BYTE_SWAP

    // C compiler intrinsic

return __byteswap(word);

#else

return ((word >> 24) & 0x000000ff) |

           ((word <<  8) & 0x00ff0000) |

           ((word >>  8) & 0x0000ff00) |

           ((word << 24) & 0xff000000);


#endif

}


为第一部分生成的代码非常简单明确;只有一个指令。


byteswap:

  byteswap x10, x10

  c.jr ra // return from function


第二部分在RV32IMC上的十二个指令中完成。X10s 保留一个词的值,并且它最后也保留返回值。


byteswap:

  srl x15, x10, 8

  lui x14, %hi( 65280 )

  add x14, x14, 65280 & 0xfff

  c.and x15, x14

  srl x14, x10, 24

  c.or x15, x14

  sll x14, x10, 8

  lui x13, 16711680>>12 &0xfffff

  c.and x14, x13

  sll x13, x10, 24

  c.or x14, x13

  or x10, x14, x15

  c.jr ra // return from function.


这不仅提高了该应用程序的性能,还显著减小了代码大小。您可以有一些类似的指令,包括种群计数(pop-count)、各种位操作类指令、控制指令等。


下一部分将介绍 Studio 如何处理自定义 ISA 扩展。


4、Codasip Studio


Studio 是一款用于处理器设计的EDA 工具,被多家领先公司用于创建特殊处理器,被 Codasip 用于设计 Bk RISC-V 内核。它可以生成SDK 中的所有必备工具,以及处理器在 Verilog、SystemVerilog 或 VHDL 和基于 UVM 的验证环境中的实现。所有这些输出都从CodAL和CodAL™中的处理器描述生成。CodAL 是一种基于 C 语言的混合体系结构描述语言。CodAL 不仅捕获 ISA 本身,还捕获处理器的资源和处理器微体系结构的其他细节。


每个处理器描述由两部分组成:处理器的一个功能模型和一个实现模型。这两个模型共用共同的部分,如操作代码或指令编码。更重要的是,这些模型同样使 Studio 能够生成基于 UVM 的验证环境。


当涉及到 ISA 扩展时,设计人员通常从CodAL中编写的成熟 RISC-V 兼容处理器开始,该处理器由 Codasip 提供。他们需要做的只是添加自定义 ISA 扩展。请注意,我们在内部也使用 Studio来构建我们自己的RISC-V合规处理器。


该过程首先确定合适的自定义指令。有许多方法可以做到这一点;一种便捷方式是使用Studio中的探查器。设计器在现成的处理器上运行关键应用程序,探查器提供表示计算热点的特定指令序列以及需要大量计算时间的函数列表。此信息可帮助设计人员添加新指令。


第一步是更改处理器的功能模型。设计器需要定义指令的汇编和二进制形式。然后,至关重要的是,指令的语义。其语义也可用 CodAL 编写。


在字节交换示例中,假设 32 位 RISC-V,该代码将显示如下:


element i_comp_2reg {

  // use of two registers

  use xregs as dst, src;

  // textual form of the instruction

  assembly { "byteswap" dst "," src };

  // encoding of the instruction

  binary { PADDING src  OPC_BYTESWAP[OPC_FRAG1] dst

OPC_BYTESWAP[OPC_FRAG0]};

  // behavior of the instruction

  semantics {

// input from register

    uint32 val;

    codasip_compiler_builtin();

    codasip_preprocessor_define("ISA_BYTE_SWAP");

// read the input from registers

    val = rf_gpr_read(src); 

// do the computation and store the result to the register

    rf_gpr_write(dst, val[ 7.. 0] :: val[15.. 8] ::

                      val[23..16] :: val[31..24]);

    };

};


下一步是定义实现。让我们考虑在一个时钟周期内执行整个指令简单直接地实现。这里唯一的任务是更新 ALU。


...

  case ALU_BYTESWAP:

    ex_result = alu_op1[ 7.. 0] :: alu_op1[15.. 8] :: 

                alu_op1[23..16] :: alu_op1[31..24];

    break;

  ...


一旦我们提供了CodAL 描述,Studio 就可以生成基于 UVM 的验证环境、 SDK和实现中所有工具。


SDK 中最重要的工具之一是 C 编译器。Codasip使用LLVM 和 GCC;通常,为 LLVM 编译器生成新指令。在这种情况下,我们可以看到 LLVM 识别字节交换的模式,并在指令语义的中间代码中使用 bswap函数。生成的代码将表示如下:


def i_comp_2reg__regs__regs__: 

  CodasipMicroClass_<(outs regs:$op0), (ins regs:$op1)>

{

  let AsmString = "byteswap $op0, $op1";

  let Pattern = [(set regs:$op0, (i32 

      (bswap (i32 CheckFI_i32_regs:$op1))))];

  let Size = 4;

  let isReMaterializable = 1;

  let mayLoad = 0;

  let mayStore = 0;

  let AddedComplexity = 1;

 }


所有其他工具都知道该新指令,因此汇编器和反汇编器、调试器和探查器也可以识别字节交换指令。


关于在HDL中的实现,Studio支持三种主要的HDL语言:Verilog、SystemVerilog和VHDL。字节交换示例生成的 Verilog代码如下所示:


always @(*) begin

    case ( alu_opcode )

...

// <file>.codal:<line>:<column>

4'h9: mux_ex_result_D = {alu_op1_Q[ 7: 0],alu_op1_Q[15: 8],

                             alu_op1_Q[23:16],alu_op1_Q[31:24]};

    ...

    endcase

end


如图所示,Studio基于 CodAL 代码生成所有必要的CodAL输出。生成 SDK 和 RTL 完全自动完成。


最后一步是验证。Studio 包括功能视图和实现视图。功能视图用于参考模型,实现视图用作 DUT,这表示生成的实现将针对参考模型进行检查。Studio生成基于 UVM 的环境,这需要一些刺激因素。Studio 附带了一组广泛的预定义测试,它还支持生成随机指令流,包括自定义指令流。设计人员也可以添加自己的直接测试。三个源(预定义测试、生成测试和直接测试)) 确保全覆盖,包括非典型极端情况。


5、用例:针对音频处理优化的处理器


许多常用的算法在通用内核上性能不是很好。典型的示例是用于信号处理、加密和机器学习的示例。一个实例是,Microsemi 有兴趣使用 RISC-V 来取代其音频处理产品系列中著名的商用微控制器内核。


在新一代产品中,他们面临着多种业务挑战:


•物联网 (IoT) 应用需要低功耗。

•希望最大限度地降低处理器 IP 成本,特别是消除版税。

•旨在最大限度地降低制版和衍生设计成本。

•旨在提高上市时间。

•希望提高计算性能和代码密度。

•由于缺少 ISA 版税,RISC-V因成本而成为有吸引力的选择,评估了用于音频处理的各种核心选项。这些测试以最小的Codasip  Bk3 RISC-V内核为起点,并使用Codasip Studio添加一些标准扩展以及自定义指令。


chapter_5_graph_添加指令的影响.png


起点是最少的RV32I 指令集。相应的基本配置 RISC-V 内核具有 16k门(Gate)。由于基本指令集没有乘法指令,这些算法包含许多乘法,指令,计算性能太慢也就不足为奇了。


添加乘法扩展 RV32IM 并使用顺序乘法器可提高性能 4倍,同时将核心区域增加20%。使用并行乘法器产生的结果为具有60%禁区的原始RV32I 内核之性能的13倍。    


使用乘法扩展和硬件乘法直观合理。然而,真正的改进是在分析软件和设计一组自定义DSP扩展之后推出。这两类任务均可在Studio完成。


分析生成特定域的处理器后,最终性能比原始处理器增强 56倍,而只需要 2.4倍的门数。这种性能改进在门数方面成本不高,非常经济高效。不仅如此,而且代码大小减少到基本配置的26%。  


通过最小化组合内核和指令内存区域,客户能够管理其硅成本和功耗。事实上,他们能够避免迁移到更昂贵的过程节点。


6、用例:加速加密算法


为了进一步说明仅用一条指令扩展一个RISC-V内核可以提供可量性改进,让我们考虑为Veridify(原为SecureRF) 的Walnut数字签名算法(WalnutDSA)扩展一个Codasip Bk3内核进行身份验证的情况。与其他加密算法一样,RISC-V 上的Walnut DSA 性能比预期要长。共同调查发现了伽罗瓦域 (32)中乘法运算存在瓶颈,即,它需要 24 个周期,其中有一个周期是可取的。


在 CodAL 中定义了一个单周期指令(quad_gmul32),并且由 Studio 以组合逻辑实现。为新指令创建了一个包装器,并且该算法也像以前一样使用。

改进后的Bk3 RISC-V处理器比原始版本大~2%,但它的速度提升了3倍。代码大小也减少了 30%,这将改善指令内存的面积和功耗。


7、结论


特定域的处理器正在成为一种可提供额外处理性能的硅高效方式。RISC-V ISA 由于其模块化和内置的自定义指令支持,所以成为创建此类处理器的理想之选。RISC-V ISA 提供广泛的 ISA 组可供选择,只有基本组 (I/E) 是必需的,其余的均为可选。这个概念允许设计师精确选择他们需要的内容。如果这仍然不足以达到预期的结果,RISC-V 规范允许添加额外的指令,同时保持 RISC-V 合规。这是一个显著优势,使您能够重用社区软件堆栈,并仅加速关键部分。


添加自定义指令可以手动完成,但这是一项耗时且容易出错的任务,还需要大量资源。Codasip用它的EDA工具Codasip Studio来解决这个问题。RISC-V 处理器和任何添加的自定义指令在高级体系结构描述语言CodAL中描述,然后 Studio 使用该语言生成 SDK 和实现处理器。高度自动化允许在数小时、数天或几周内添加新指令。


与现成的处理器内核相比,使用 RISC-V 自定义指令创建的特定域处理器效率非常高。在音频处理示例中,门数增加 2.4倍,性能提高 56倍。添加一个单指令,数字签名算法的速度会加快 3倍 。在其他应用领域也取得了类似的进展。为了产生可测的独特改进结果,跨域使用Codasip Studio没有限制。

赞助企业