2412d,d的8月会议

发布于:2024-12-19 ⋅ 阅读:(14) ⋅ 点赞:(0)

原文

总结

替换D的逃逸分析

Rikki说,他一个月前曾与Dennis讨论过简化D的逃逸分析,但没有结果.在BeerConf上,他再次提起了它,Dennis他一直在考虑它.

Rikki也与Walter谈过这件事,Walter曾说过DIP1000并没有完全如期工作,且有点太复杂了.

因此,Rikki想讨论按D逃逸分析方法替换DIP1000的可能性.在做出可靠的决定前,第一步是确保它完全在预览开关之下.丹尼斯证实当前是这样.

Rikki说,下一步是考虑切换它它可能的样子.他请求建议.

Dennis说,在决定如何切换它前,应该首先说明当前设计原因及切换的目标.他说他有一些问题.一个是缺乏传递域.

另一个问题是,即使结构有多个成员,它们也只有一个生命期.他一直在考虑允许按注解结构字段,但他还没有具体的提议.

Walter说,他遇见的困难不是DIP1000复杂,而是语言复杂.必须适配语言的各种构造.引用类型工作原理隐式类类型懒参数构造器这就是复杂性的来源.

他给出了成员函数的隐式参数的示例.如果有人想了解如何在构造器或成员函数中使用DIP1000,他一遍遍地解释说,则只需要按显式参数一样,把它写出来.

然后就能看到它应该是如何操作的.但人们发现这无休止地困惑.

简化它的提案还必须证明它如何可能比现在的DIP1000更简单,因为DIP1000很复杂,因为语言很复杂.它必须支持每个语言结构.

Rikki说,逃逸分析分为三个不同级.最基本级是"这是一个而它帮助输出输出".然后你就有了语言可推导出的东西.

然后就有了你可添加可证明的东西.现在真没有那个规模,所以现在当事情太宽泛时,没有逃避的机会.

walter重申,DIP1000复杂性因为语言的复杂性,而不是概念自身,这非常简单.如果用指针写出来,一切都会很清晰和简单.

当你添加像auto ref此东西时,它开始复杂.他从来不喜欢auto ref,也从没用过它,因为它太怪了.

他说,如果Rikki能想出更好方法来完成,他会支持.DIP1000是他最好的机会.

Timon说,DIP1000可以说已承担了一些可注解不同级间接的复杂度成本,但一般禁止这样.应有更好的权衡.

Walter说有两种间接:指针和引用.这使得DIP1000复杂性增加了一倍.Timon同意,但表示即DIP1000不是你在按指针转换所有内容得到的结果.

DIP1000比这更进一步,因为实际上每个指针都有两级间接性,但不是按正交限制它.根据构造注解任一间接级.

Walter同意,并说这是因为引用隐式的间接性,而指针则没有.他问可做些什么.
Rikki让每个人都说他们的想法.

Quirin说,他理解DIP1000目标是你可取局部变量的地址,比如静态数组等,且按域限定指针无法逃逸.

因此,在DIP1000默认值未来版本中,可能会有个编译器开关禁止它,这样禁止取局部变量的地址.

他说他遇见的问题是,如果有系统函数,但实际上没有按@系统注解它,然后有域注解,编译器会认为你正确处理了域操作.

如果你不是,你就完蛋了.而意外很容易发生.

这是DIP1000的一个问题.你可在系统代码坑自己.如果不是在安全代码做对了,但如果是初学者,没有用@安全注解某些东西,然后使用了它,如,是隐式域-preview=in,就会遇见麻烦.

所以可有选项禁止它们,但在代码中允许像@安全一样的所有域检查等会很好.

沃尔特说,@系统关闭了所有检查,因为有时需要做一些烦人事情.初学者不应编写@系统代码.Quirin说,如果不使用@safe,DIP1000会使该语言更加危险.

这就是有些人搞不来的原因.

Walter认为最大的问题人们不喜欢写注解.只在没有函数体时,它们是必需的.如果只是取本地地址,编译器会说,“好的,现在是域指针了”.

它会自动这样.困难在于有两个地方需要添加注解:没有函数体时和在虚函数中.这时,编译器无法自动这样.

Walter说,语言最近有了变化,允许对局部变量使用引用.这允许无需注解,更高的安全性.这是一件好事.它通过减少原始指针的需求改进语言.

下一步是允许构字段上的引用.必须弄清楚它的语义,但是越能改进语言以减少使用原始指针,它自身就越安全,问题就会越少.

Adam说有人建议不要在打开DIP1000时构建Phobosv3.他有点同意该观点.他前曾告诉Walter,DIP1000不值得.

Rikki想说明,如果没有引用计数,基本上不可能每秒处理100,000个请求.这是由Walter在物主逃逸分析方面的工作所控制的,而这反之又以逃逸分析为主题的.

所以他在这方面被阻塞了,因此想要排序逃逸分析.

Walter说,ROI如此之低的原因是,因为栈中错误指针,人们很少在程序中遇见易错漏洞.Mathias问为什么花这么多时间在上面.

沃尔特比作飞机失事:它们很少见,但一旦发生,就会造成灾难性的后果.你不可能既是内存安全的语言,又这样.

Mathias说,DIP1000使他不想使用D,因为当他使用vibe.d允许D时,他得到了大量的弃用.这太可怕了.他希望默认不打开.

当谈到DIP自身时,他说该组合就是不管用.需要他在类型定义中使用注解他的类或结构的设计在到达时都死了.

他说,很多人把它与比较,这是错误的比较.是由外到内,但是由内到外.因此,如果你的外层且你组合了一个有多个层的类型,则你的所有层都是.

,情况正好相反.无法在语言中表示域的深度.这在语法上是不可能的.它就是无法工作的.

更新:稍后开会并决定需要做两件事向前步进:编制一份失败的DIP1000案例列表,看看是否可解决它们;并考虑如何默认推导.

std.math移动到core.math

Martin说他多年来一直想将std.math移动到core.math.很久以前,在GitHubPR中与Walter的讨论中提到了它,他记得Walter也同意它.

最近,再次试使编译器测试包独立于Phobos.现在,现在DMD运行时同一个仓库中,因此所有make目标都是不依赖Phobos独立的,这样运行编译器测试,那就太好了.

做了实验,发现测试用例中的大多数Phobos导入都是std.math.一个常见原因幂符号^^.还有一些测试测试了数学内置函数.

CTFE的编译器使用混杂的函数名,检测到调用标准数学函数.这已是个问题,因为当更改std.math中的属性时,因为新混杂名,也需要更新编译器.

因此,测试了所有这些方法是否有效,而CTFE数学结果符合期望.因此,有隐性依赖Phobos.

Phobos导入所有内容转发core.math,它已在运行时中存在.它当前有大约五个函数.

LDC已转发了一些数学函数.std.math是为数不多的LDCGDC只是为了可使用内联函数,而有一些修改Phobos模块之一.

移动进运行时会更好,因为可最小化或清除,Phobos分叉的需求.
Walterstd.math类似一个包含很多东西手提袋.他建议将应该是core.math的内容移动到d运行时中并转发到这里,然后按使用core.math更改测试包.

他想保存std.math.仍有很多编译器测试包不需要的数学函数,可在那里保存它们.

Jonathan说,过去当决定真想要在d运行时中导入Phobos中的东西,但真想人们导入Phobos时,就把该东西移到了core.internal.
如,std.traits导入了core.internal.traits以避免重复d运行时中使用的特征,用户仍可通过std.traits来取它.

实际上,std.math中的大多数函数都是由编译器检测到的.

据他所知,std.math相当孤立的,不依赖Phobos中的其他东西.他会仔细检查,但他确信,所以可把它移过来.

真不想分开它.如果它在运行时,则直接从那里包含合乎逻辑的,从某个特定的编译器版本开始,并保存它,在PhobosAPI中呆一段时间实现后向兼容.
所以最终位置将在core.math中.

Walter说,很简单:如果想在编译器测试包放置它,它需要进入运行时.Martin说他需要检查,但这会是大部分函数.

Mathias认为尽管不能解决Martin的问题,但应该去掉幂符号.Martin说,移动它到运行时,可清除在未导入std.math试用它出错的特例.

沃尔特同意马蒂亚斯的意见,认为应该淘汰它.这是丑陋的.

Adam说,Phobos3改变绝佳机会.这是自然的分界线.可保持标准库2原样长期支持它,但Martin可在标准库3为所欲为.

Adam已在看std.math思考他有多害怕移植它.因此,如果Martin想出其他东西并告诉他如何让它有效,他就会让它有效.

主要类型语法DIP

Quirin和一起讨论了他的.12.

基本思想是,不更改语义修改语法.它为了确保可由错误消息表示的任意类型,(如)也可在代码中表示,且你不会收到解析错误.
Quirin说他已为该提案提供了实现,且按期望实现引用.他已试了很久,并真正试突破了一些极限.他没有发现问题.

他说,同样问题也适合链接.像一个带extern(C)链接的函数指针.
他说也许Quirin已解决了它,但要求他检查一下语法和括号问题,并确保提案没有这些问题.
Walter说,在编译器测试包试它将很好.奎林同意.

“让printf安全的DIP

Iain说,现在是2024年,人们仍在发明新的CPU.他说中国人发明了他们自己的MIPSCPU,他们不得不把旧的GDC版本拖出来,并移植到他们的CPU上,只是为了让LDCDMD正常工作.
这是另一个崭露头角的现代芯片(龙芯).让这些人对拥有现代版本D编译器而不是C++编译器满意,这样他们就可跳到最新版本.

因此,较旧的bootstrap版本完全无价值.

沃尔特说好.确保D编译器源码安全并不重要.这只是他想做的事情.但是,如果会导致很多下游问题,则当然,我们还能做什么?

Iain说必须让文档非常响亮和显式.GDC在这方面做得很好,它解释了如果从给定版本的编译器开始,你必须做什么,因为某些版本GDC是使用特定的C++标准编写的.

取得最新版本,必须从起点开始浏览这些版本.也应该同意,对DMD同样.

Rikki说明,Elias已完成了LDC的新docker版镜像,该镜像完成了从LTS版本到最新版本的引导.他说应该可按C++代码基转储编译器,然后用来引导相同编译器版本.

他已考虑了很久了.这在今天不是问题,但未来会变成一个问题.

使用printf真很简单.这只是一个调用函数:在栈上压几个参数,调用一个函数,完成.

Dennis问,是否为DMD创建了writeln最小模板版本,因为DMD大多只连接串,偶尔会构成一个整数.Walter说可编写自己的printf,但C标准库中的那个是经过实战检验,调试和优化最多的.

Dennis强调只需要连接串.
Johanthan建议把它包装起来.
他同意Walter所说的writeln有问题,因为它是模板的暴风雪.但他不断从人们那里听到不应删除这些模板.

Walter重申printf受到了很大的恶意,但它是历史上调试,优化最多的函数.也许可实现一个只是调用安全转发到printfwriteln.

它有它的问题,因此提交安全printf提案.
他说Jonathan完全正确的,模板writeln带来了很多好处.他不是在反对它.但是在试调试编译器时,处理writeln是个巨大的痛苦.

因此他总是回到printf的原因.他不想编译器依赖writeln,因为那样无法引导编译器.

Jonathan同意不想DMD依赖标准库.此时,也许用带串并按C串的东西转换它来包装printf可行的.

Walter说这就是安全printf提案的作用,它只是让编译器覆盖printf式以使其内存安全.Jonathan说可避免直接使用包装器调用printf.
总之,编译器一般情况不同.

空初化一个引用变量

Dennis问大家是否都同意初化引用变量应该是一个错误.DIP没有具体说明,它没用例.沃尔特说那是个错误.没人反对,这里.

域和自动引用

Dennis问大家是否都同意变量上的auto ref关键字必须放在一起,而不是与不同域内关键字一起使用,如auto { ref int x = 3; }沃尔特说是的,干掉它.

Quirin说他注意到,在查看语法时,引用并不总是需要彼此相邻.如,可在参数列表中编写ref const auto foo.他建议应该禁止这样.沃尔特说应该弃用它.