没有外部内核文件的openCL

openCL without external kernel file

本文关键字:openCL 文件 内核 外部      更新时间:2023-10-16

我想创建一个OpenCL内核,而不给最终用户访问它。

因此,我不能使用常规的外部.cl文本文件。有什么替代方案,关于我想避免创建一个巨大的文本字符串与内核?

还有一个问题,如果我把这段代码放在一个硬编码的字符串中,难道不可能从一些反汇编器中访问这段代码吗?

这里有两种情况:

  1. 如果您的目标是单个设备
  2. 如果您的目标是任何OpenCL设备

在第一个场景中,有可能将二进制数据嵌入到可执行文件中(使用字符串)。并在运行程序时加载它。逆向工程是不可能的(除非是已知的,比如汇编),因为程序将编译代码,而不是您编写的原始代码。

这样做的方法是:

uchar binary_dev1[binarySize] = "..."
uchar * binary = &binary_dev1;
program = clCreateProgramWithBinary(context, 1, &device, 
                                    &binarySize, 
                                    (const unsigned char**)&binary,
                                    &binaryStatus,
                                    &errNum);

第二种选择涉及通过某种"mangling"来保护内核中的源代码。由于mangler代码将被编译,因此逆向工程可能会很复杂。

你可以做任何你能想到的可逆的变形,甚至把它们组合起来。一些想法:

  • 使用压缩格式压缩代码,但硬编码解压缩的一些参数,使其不那么简单。

    • LZ4, ZLIB等
  • 对代码使用异或操作符。如果它随时间变化更好,如果它使用一个不明显的规则变化更好。

    • 例如:
      char seq = 0x1A;
      for(int i=0; i<len; i++){
          out[i] = in[i] ^ seq;
          seq = ((seq ^ i) * 78965213) >> 4 + ((seq * i) * 56987) << 4;
      }
      
  • 使用需要密钥的编码方法进行编码,并且是可逆的

  • 使用一个程序来保护你的程序二进制进行逆向工程,如Themida。
  • 为OpenCL 1.2使用SPIR 1.2或为OpenCL 2.0使用SPIR 2.0,直到OpenCL 2.1的SPIR- v可用。