当前位置: 首页 > news >正文

toy.struct_constant和toy.struct_access

在有了类型存储层StructTypeStorage后,编译器中还必须有具体的操作(Operations,简称 Ops)来创建和访问这个结构体。

在 MLIR Toy Tutorial 中,针对!toy.struct自定义类型,精心设计了两个互补的核心算子:toy.struct_constanttoy.struct_access。它们在计算图中分别扮演着“生产者”与“消费者”的角色。


1.toy.struct_constant—— 结构体的“生产者”

在编译器中,当用户在代码里写下类似于var a = [[1, 2], [3, 4]](假设这是一个结构体字面量)时,编译器需要在一个算子中把这些常量值打包封装起来。toy.struct_constant就是干这个活的。

📌 IR 展现形式

它在 MLIR 文本文件中长这样:

%0 = "toy.struct_constant"() { value = [dense<[1.0, 2.0]> : tensor<2xf64>, dense<3.0> : tensor<1xf64>] } : () -> !toy.struct<tensor<2xf64>, tensor<1xf64>>
  • 输入:它不需要运行时输入参数(括号内为空())。
  • 属性(Attributes):它携带了一个编译器静态已知的属性value,里面是一个数组,包含两个具体的稠密张量常量(dense<...>)。
  • 输出类型:返回一个完整的、带有具体成员类型签名的!toy.struct

🛠️ TableGen (ODS) 定义

Ops.td中,它的定义重点在于约束它的value属性和返回值类型:

def StructConstantOp : Toy_Op<"struct_constant", [Pure]> { let summary = "结构体常量生成算子"; // 关键属性:存储具体数据的 ArrayAttr let arguments = (ins ArrayAttr:$value); // 关键输出:输出必须是一个 Toy 结构体类型 let results = (outs Toy_StructType:$output); }

2.toy.struct_access—— 结构体的“消费者”

有了结构体,程序总得去读里面的数据。toy.struct_access类似于 C 语言中的点运算符(如my_struct.member),专门用来根据索引(Index)提取结构体中的某个特定数组成员

📌 IR 展现形式

// 语义:从刚才生成的结构体 %0 中,提取索引为 0 的那个成员 %1 = "toy.struct_access"(%0) { index = 0 : i64 } : (!toy.struct<tensor<2xf64>, tensor<1xf64>>) -> tensor<2xf64>
  • 输入:接收一个已经生成的!toy.struct变量。
  • 属性(Attributes):携带一个静态的整数属性index,表明我们要拿第几个成员(从 0 开始计数)。
  • 输出类型:它的输出类型(这里是tensor<2xf64>)必须严格等于该结构体中对应索引位置的那个类型。如果类型对不上,MLIR 的验证器(Verifier)就会报错。

🛠️ TableGen (ODS) 定义

def StructAccessOp : Toy_Op<"struct_access", [Pure]> { let summary = "结构体成员访问算子"; // 输入:一个结构体对象 + 一个静态的索引值 let arguments = (ins Toy_StructType:$input, I64Attr:$index); // 输出:解包后的任意 MLIR 类型(通常是底层 tensor) let results = (outs AnyType:$output); // 必须声明自定义的验证逻辑 let hasVerifier = 1; }

3. 核心硬核点:struct_access的 C++ 验证器(Verifier)

由于 MLIR 强调强类型安全,你不能随意去 access 一个不存在的索引,或者宣称拿出来的类型与结构体内部存的类型不一致。因此,博客在介绍struct_access时,一定会重点贴出它的 C++verify()函数实现:

LogicalResultStructAccessOp::verify(){// 1. 获取输入结构体的类型指针autostructType=llvm::cast<StructType>(getInput().getType());// 2. 获取你想要访问的 index 值uint64_tindex=getIndex();// 3. 安全检查:索引不能越界if(index>=structType.getElementTypes().size())returnemitOpError()<<"访问越界!结构体只有 "<<structType.getElementTypes().size()<<" 个成员";// 4. 类型强一致性检查:算子声明的输出类型 必须等于 结构体该位置的真实类型Type expectedType=structType.getElementTypes()[index];if(getOutput().getType()!=expectedType)returnemitOpError()<<"类型不匹配!期望获得 "<<expectedType<<",但算子输出声明为了 "<<getOutput().getType();returnsuccess();}

4. 它们在 Lowering(阶段性降低)时去哪了?

当编译器把代码向下推进到LLVM Dialect(底层中间表示)准备对接libc或生成汇编时,这两个高层算子会发生巨大的蜕变:

  • toy.struct_constant:在高级抽象中它是一体化的。降低到低层时,它会被完全解构(Flatten)。编译器会分别为内部的每一个 Tensor 常量生成底层的llvm.mlir.global全局静态内存,并生成一个llvm.struct把这些内存描述符指针打包装进去。
  • toy.struct_access:会被直接映射并降低为 LLVM Dialect 的llvm.extractvalue指令。该指令在硬件物理层面非常高效,它直接通过相对结构体基地址的偏移量(Offset),一条指令把目标成员的内存指针给抠出来。

💡 总结

struct_constantstruct_access是高级语言复合类型在编译器中间表示(IR)里的具体体现。一个负责把离散的数据包起来,一个负责按图索骥把数据掏出来。有了它们,MLIR 才能在高级图层面上完成复杂的结构体数据流分析与优化,并在最后一刻安全地交付给底层的llvm.struct和硬件寄存器。

http://www.jsqmd.com/news/1202001/

相关文章:

  • 如何轻松导出原神祈愿记录:免费开源工具的完整指南
  • 雷达中国官方售后服务中心维修地址和服务电话实地考察报告+多信源验证(2026年7月最新) - 亨得利钟表维修中心
  • ARC-AGI抽象推理测试:5个实战技巧助你成为AI基准开发高手
  • 亨得利官方服务项目及价格查询|地址和24小时电话权威信息通告(2026年7月更新) - 亨得利官方
  • 30万级插混SUV对比:沃尔沃XC70 vs 比亚迪唐DM-p vs 理想L7,插混SUV推荐哪款? - 信息情报站
  • 终极指南:3分钟掌握QQ聊天记录数据库解密全平台解决方案
  • 中文大语言模型技术架构演进:从通用底座到垂直领域智能体
  • 2026年Q3工业警示与指示照明行业观察:苏州杭焕自动化设备有限公司的全链路服务价值解析 - 企业推荐官【官方】
  • android 输入系统
  • 新手电子鼓选购指南!4大核心部件+4款长效机型推荐
  • 网络攻击工具深度解析:Zarp框架架构与实战应用指南
  • 食品包装线实战:C#上位机+国产PLC落地自动化,这份避坑指南请收好
  • Howl编辑器多语言支持:50+编程语言语法高亮与自动补全
  • 西安劳力士回收价格查询和靠谱平台实测排行(2026年7月最新) - 天价名表回收平台
  • JupyterLab变量监控插件:数据科学家的终极调试神器
  • 从单体到分布式:Apache Kyuubi的多租户架构转型与数据服务价值实现
  • 国内 GEO 赛道天花板!人数最多、权威性拉满的汇搜社全域搜索优化社群完整解析 - 速递信息
  • 鸣潮游戏自动化工具ok-ww:解放双手的智能辅助解决方案
  • 三步解锁123云盘VIP特权:终极免费解决方案,快速享受会员下载
  • 江西南昌美术培训专业的机构是哪 - GrowUME
  • 如何高效解锁B站缓存视频:m4s-converter完全解析与实战指南
  • datascience数据聚合分析:分组统计与汇总的实用教程 [特殊字符]
  • 免费API资源宝库:730+接口助你快速构建应用
  • 5步掌握:如何快速搭建云安全实战环境,提升攻防能力
  • 上海百达翡丽回收价格查询和各大回收平台实测排行(2026年7月最新) - 嘉价奢侈品回收平台
  • 跨界融合:用Rust的静态优雅重构Lua的动态灵魂
  • 100个练习掌握Rust编程:从零到精通的完整学习指南
  • GTA IV FusionFix终极指南:一站式解决完整版技术难题与性能优化
  • 2026瑞安黄金回收避坑实录:塘下、安阳、莘塍、仙降、阁巷正规回收渠道整理 - 不晚生活号
  • Agent 的上下文继承:子 Agent 如何获取和传递父 Agent 的中间推理结果