该项目旨在开发一个 Perl 编译器,将 Perl 代码转换为 Java 字节码并在 Java 虚拟机 (JVM) 上执行。虽然该项目仍处于积极开发阶段,但它提供了一个在 JVM 环境中运行 Perl 脚本的实验平台。
主要目标
- 在 JVM 上无缝执行 Perl 脚本:主要重点是实现在 JVM 上执行中小型 Perl 脚本,提供一种将 Perl 与基于 Java 的生态系统集成的独特方法。
- 探索 Perl 和 Java 的互操作性:该项目充当 Perl 和 Java 之间的桥梁,允许开发人员尝试两种语言之间的交互。
- 编译器设计和字节码生成:该项目为那些对编译器设计和字节码生成复杂性感兴趣的人提供了一个平台,利用 ASM 库进行动态 Java 字节码创建。
当前限制
该项目是将 Perl 引入 JVM 的一次雄心勃勃的尝试,但重要的是要对其当前状态和范围设定现实的期望:
- 模块支持有限:编译器不支持 XS 模块或许多 CPAN 库,尤其是那些严重依赖 C 扩展的库(例如、、和Moose)DBI。这限制了其运行依赖于此类模块的复杂 Perl 应用程序的能力。List::UtilSocket
- 专注于中小型脚本:该编译器最适合不依赖大量模块依赖关系或深度 Perl 功能的较简单的 Perl 脚本。大型 Perl 应用程序(尤其是那些涉及大量模块使用的应用程序)超出了其当前的能力。
- 语法兼容性:虽然编译器处理了 Perl 的许多核心功能,但它可能不完全支持高级语法更改模块或 Perl 的一些更深奥的功能。
- Perl 的简易替代品:它并非旨在替代 Perl 或成为完整的 Perl 解释器。相反,它是一个实验性工具,可在 JVM 中提供类似 Perl 的环境。用户不应期望与本机 Perl 完全向后兼容。
- 具有 Perl 知识的 Java 开发人员:如果您是熟悉 Perl 的 Java 开发人员,则该项目提供了一种将 Perl 脚本集成到 Java 应用程序的有趣方法。
- 编译器和语言爱好者:那些对将高级语言翻译成 JVM 字节码的过程感兴趣的人可能会发现该项目的方法和方法很有启发。
- 实验者和修补者:如果您喜欢实验语言互操作性或者正在寻找在 JVM 上运行 Perl 脚本的独特方法,那么这个项目可能是一个值得探索的有趣工具。
特征
该编译器目前支持几个关键的 Perl 功能:
- 闭包:支持匿名函数和词法变量闭包,允许封装代码。
- Eval-string:动态执行 Perl 代码,支持基本表达式和语句。
- 语句、数据类型和调用上下文:处理常见的 Perl 语句(例如if、foreach)、数据类型(例如标量、数组、哈希),并维护 Perl 的上下文敏感性(例如标量与列表上下文)。
模块
词法分析器和解析器
- 词法分析器:用于将代码分成空格、标识符、运算符等符号。
- 解析器:拾取符号并将它们组织成块、子程序等对象的抽象语法树 (AST)。
- StringParser 用于解析 Perl 中的特定领域语言,例如 Regex 和字符串插值。
- ClassWriter:用于生成类的字节码。
- 用户代码被翻译成方法。
- 使用自定义类加载器加载生成的字节码。
- EmitterVisitor:用于生成方法内操作的字节码。
- 它遍历 AST 并生成相应的 ASM 字节码。
- EmitterContext:保存符号表的当前状态和调用上下文(void、标量、列表)。
- PrinterVisitor:为 AST 提供漂亮的打印字符串化。
- 代码块、变量声明和操作的 AST 节点表示。
- SymbolTable和ScopedSymbolTable:管理变量名称及其对应的局部变量索引。
- 运行时:提供 Perl 标量变量、代码、数组、哈希的行为的实现。
- main 方法生成程序主体的字节码。
- 生成的方法作为代码引用加载到变量中并执行。
- PerlScriptEngine是一个 Java 类,允许您使用 Java 脚本 API (JSR 223) 执行 Perl 脚本。
网友
1、在阅读说明时,它提到了 "perl 脚本"--这让人联想到它将是读取 stdin、打印到 stdout 的单个小文件,中间不会做太多其他事情。
它还提到了它如何不支持 XS 模块或 CPAN。 这确实限制了它的支持范围。 它可以处理小片段,但不能处理大型应用,也不能处理任何需要改变语法的大型模块。 不涉及任何 XS 代码。 Socket 是 XS。 List::Util 是 XS。
我敢打赌,光是这两项,就切断了人们可能想要运行的 95% 的东西。
这通常就是所有这些东西的弊端所在。 用类似 Perl 的语法和变量等编写类似 Perl 语言的引擎相对容易。 但这并不能运行真正的大型 Perl 程序,因为这些程序都有很多语言表面语法之外的依赖关系。
当然,能运行小型脚本的引擎已经足够令人印象深刻了;但先别指望能迁移你的百万行网络应用系统;)
2、我不记得有认真尝试将 Perl 移植到 JVM。我能记得的最接近的一次是 Stevan Little 的 Moe 项目,它是一种针对 Scala 的 Perl 衍生语言。
Parrot 和 PONIE 的意图是制作一个类似于 JVM 的新VM,但专门针对动态语言的需求进行调整……然后将 Perl 5 放在其之上。事实证明,这比预期的要困难得多,在某种程度上,我认为这是因为 Perl 的实现抽象泄漏到了语言中。
Larry 之前曾致力于将 Perl 集成到 Java 中,但那并不是关于通用虚拟机的。我忘记了所有细节,但肯定比那要早得多。那件事没有进展,我不知道它与这个新项目有多相似。
1997 年冬季版的《Perl Journal》上有一篇关于此的文章,作者是 Brian Jepson。这是使用 RMI 从 Java 调用 Perl 的一种方法。
还有 Bradley M. Kuhn 关于“B::JVM”的工作。Kuhn 撰写了一篇关于研究不同方法的硕士论文以及一些 TPJ 文章。Larrry Wall 是 Kuhn 论文委员会的成员。
3、Parrot 被 MoarVM 取代了,MoarVM 是Rakudo 运行的主要VM。但 Rakudo(当前唯一的编译器)也可以编译到 JVM 和 JS 后端。
4、值得注意的是,fglock 还拥有 Perlito 项目,这是一个将 Perl 源代码转换为 Java 源代码的转换器。这会跳过源代码并转到 JVM 字节码。
5、我一直在向那些醉心于热情的 Rust 黑客们提倡,他们应该实现一个 Perl 解释器。