是否可以用 Java 编写设备驱动程序?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/683701/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-11 17:53:00  来源:igfitidea点击:

Is it possible to code a device driver in Java?

javaoperating-systemdevice-driver

提问by Philip Stark

Introduction

介绍

I heard something about writing device drivers in Java (heard as in "with my ears", not from the internet) and was wondering... I always thought device drivers operated on an operating system level and thus must be written in the same language as the OS (thus mostly C I suppose)

我听说过一些关于用 Java 编写设备驱动程序的事情(听说是“用我的耳朵”,而不是从互联网上听到的)并且想知道......我一直认为设备驱动程序在操作系统级别上运行,因此必须用相同的语言编写作为操作系统(因此主要是 CI 假设)

Questions

问题

  1. Am I generally wrong with this assumption? (it seems so)
  2. How can a driver in an "alien" language be used in the OS?
  3. What are the requirements (from a programming language point of view) for a device driver anyway?

  1. 我通常对这个假设有错误吗?(好像是这样)
  2. 如何在操作系统中使用“外星人”语言的驱动程序?
  3. 设备驱动程序的要求(从编程语言的角度来看)是什么?

Thanks for reading

谢谢阅读

采纳答案by jalf

There are a couple of ways this can be done.

有几种方法可以做到这一点。

First, code running at "OS level" does not need to be written in the same language as the OS. It merely has to be able to be linked together with OS code. Virtually all languages can interoperate with C, which is really all that's needed.

首先,在“操作系统级别”运行的代码不需要与操作系统使用相同的语言编写。它只需要能够与操作系统代码链接在一起。几乎所有语言都可以与 C 互操作,而这正是所需要的。

So language-wise, there is technically no problem. Java functions can call C functions, and C functions can call Java functions. And if the OS isn't written in C (let's say, for the sake of argument that it's written in C++), then the OS C++ code can call into some intermediate C code, which forwards to your Java, and vice versa. C is pretty much a lingua francaof programming.

所以在语言方面,技术上没有问题。Java函数可以调用C函数,C函数可以调用Java函数。如果操作系统不是用 C 编写的(假设它是用 C++ 编写的),那么操作系统 C++ 代码可以调用一些中间 C 代码,这些代码转发给您的 Java,反之亦然。C 几乎是编程的通用语言

Once a program has been compiled (to native code), its source language is no longer relevant. Assembler looks much the same regardless of which language the source code was written in before compilation. As long as you use the same calling convention as the OS, it's no problem.

一旦程序被编译(为本机代码),它的源语言就不再相关。无论源代码在编译前是用哪种语言编写的,汇编程序看起来都差不多。只要您使用与操作系统相同的调用约定,就没有问题。

A bigger problem is runtime support. Not a lot of software services are available in the OS. There usually is no Java virtual machine, for example. (There is no reason why there technically couldn't be, but usually, but usually, it's safe to assume that it's not present).

一个更大的问题是运行时支持。操作系统中提供的软件服务并不多。例如,通常没有 Java 虚拟机。(技术上没有理由不存在,但通常,但通常,假设它不存在是安全的)。

Unfortunately, in its "default" representation, as Java bytecode, a Java program requiresa lot of infrastructure. It needs the Java VM to interpret and JIT the bytecode, and it needs the class library and so on.

不幸的是,在其“默认”表示中,作为 Java 字节码,Java 程序需要大量基础设施。它需要 Java VM 来解释和 JIT 字节码,它需要类库等等。

But there are two ways around this:

但是有两种方法可以解决这个问题:

  • Support Java in the kernel. This would be an unusual step, but it could be done.
  • Or compile your Java source code to a native format. A Java program doesn't have to be compiled to Java bytecode. You could compile it to x86 assembler. The same goes for whatever class libraries you use. Those too could be compiled all the way to assembler. Of course, parts of the Java class library requires certain OS features that won't be available, but then use of those classes could be avoided.
  • 在内核中支持 Java。这将是一个不寻常的步骤,但可以做到。
  • 或者将您的 Java 源代码编译为本机格式。Java 程序不必编译为 Java 字节码。您可以将其编译为 x86 汇编程序。您使用的任何类库都是如此。这些也可以一直编译到汇编程序。当然,Java 类库的某些部分需要某些不可用的操作系统功能,但是可以避免使用这些类。

So yes, it can be done. But it's not straightforward, and it's unclear what you'd gain.

所以是的,它可以做到。但这并不简单,也不清楚你会得到什么。

Of course another problem may be that Java won't let you access arbitrary memory locations, which would make a lot of hardware communication pretty tricky. But that could be worked around too, perhaps by calling into very simple C functions which simply return the relevant memory areas as arrays for Java to work on.

当然,另一个问题可能是 Java 不允许您访问任意内存位置,这会使许多硬件通信变得非常棘手。但这也可以解决,也许通过调用非常简单的 C 函数来简单地返回相关的内存区域作为 Java 处理的数组。

回答by vladr

Have you perhaps heard a reference to the JDDK?

您可能听说过对JDK的引用吗?

Writing a device driver 100% in Java is not possible without native codeto provide the interaction between (1) the OS-specific driver entry points and conventions, and (2) the JVM instance. The JVM instance could be started "in-process" (and "in-process" may have different meanings depending on the OS and on whether the driver is a kernel-mode or user-mode driver), or as a separate user-land process with which a thin, native driver adaptation layer can communicate and onto which the said driver adaptation layer can offload actual user-land work.

如果没有本机代码来提供 (1) 特定于操作系统的驱动程序入口点和约定以及 (2) JVM 实例之间的交互,则不可能100% 用 Ja​​va 编写设备驱动程序。JVM 实例可以在“进程内”启动(并且“进程内”可能具有不同的含义,具体取决于操作系统以及驱动程序是内核模式还是用户模式驱动程序),或者作为单独的用户空间一个薄的本地驱动程序适配层可以与之通信并且所述驱动程序适配层可以在其上卸载实际用户空间工作的过程。

回答by Mnementh

It's not impossible, but possibly hard and possibly makes not much sense.

这并非不可能,但可能很难,而且可能没有多大意义。

Possible is it, because Java is a normal programming language, as long as you have some way to access the data, it's no problem. Normally in a modern OS the kernel has a layer to allow raw access to hardware in some way. Also already exist drivers in userspace, at least the userspace-part should be no problem to implement in Java.

可能吧,因为Java是普通的编程语言,只要有办法访问数据就没有问题。通常在现代操作系统中,内核有一层允许以某种方式对硬件进行原始访问。用户空间中也已经存在驱动程序,至少用户空间部分在Java中实现应该没有问题。

It makes possibly not too much sense, because the kernel has to start a JVM to execute the driver. Also JVM-implementations normally eat up much memory.

这可能没有太大意义,因为内核必须启动一个 JVM 来执行驱动程序。此外,JVM 实现通常会占用大量内存。

You could also use Java-code compiled to be executed natively on the platform (not with the help of a JVM). This is usually not that efficient, but it could be suitable for a device-driver.

您还可以使用编译为在平台上本地执行的 Java 代码(而不是在 JVM 的帮助下)。这通常不是那么有效,但它可能适用于设备驱动程序。

The question is, does it make sense to implement the driver in Java? Or stated in another way: What is the benefit you hope for, if you use Java for implementing the driver instead of another alternative? If you can answer this question, you should find a way to make it possible.

问题是,用 Java 实现驱动程序有意义吗?或者换一种说法:如果您使用 Java 而不是其他替代方案来实现驱动程序,您希望得到什么好处?如果你能回答这个问题,你就应该想办法让它成为可能。

At the end the hint to JNode, a project that tries to implement a complete OS purely based on Java.

最后是对JNode的提示,是一个试图实现完全基于 Java 的完整操作系统的项目。

回答by dmckee --- ex-moderator kitten

It is possibleto compile java code to hardware native (i.e. not JVM bytecode) instructions. See for instance GCJ. With this in hand, you're a lot closer to being able to compile device drivers than you were before.

是可能的编译Java代码,硬件本地(即不是JVM字节码)的指令。参见例如GCJ。有了这个,您就可以比以前更接近能够编译设备驱动程序了。

I don't know how practical it is, though.

不过不知道实用性如何。

回答by JesperE

Device drivers have to be written in a language which can execute in the kernel, either compiled into it, or loaded as a module at runtime. This usually precludes writing device drivers in Java, but I suppose you theoretically could implement a JVM inside a device driver and let it execute Java code. Not that any sane person would want to do that.

设备驱动程序必须用一种可以在内核中执行的语言编写,或者编译到内核中,或者在运行时作为模块加载。这通常会妨碍用 Java 编写设备驱动程序,但我想理论上您可以在设备驱动程序中实现 JVM 并让它执行 Java 代码。并不是说任何理智的人都愿意这样做。

On Linux there are several user-land (i.e. non-kernel) implementations of filesystems which uses a common abstraction layer called (fuse) which allows user-land programs to implement things which are typically done in the kernel.

在 Linux 上,有几个文件系统的用户级(即非内核)实现,它们使用称为(熔丝)的公共抽象层,允许用户级程序实现通常在内核中完成的事情。

回答by bdd

Possible?

可能的?

Yes but only in special circumstances. Because you can write an operating system in Java and C#, and then, should be able to write device drivers for it. The memory hit to these drivers and operating systems would be substantial.

可以,但仅限于特殊情况。因为你可以用 Java 和 C# 编写操作系统,然后,应该可以为它编写设备驱动程序。这些驱动程序和操作系统的内存损失将是巨大的。

Probable?

可能?

Not likely. Atleast not in the world of Windows or MacOS or even Linux... At least not anytime soon. Because languages like C# and Java depend on the CLR and JVM. The way these languages work means that they cannot effectively be loaded into ring0.

不见得。至少不是在 Windows 或 MacOS 甚至 Linux 的世界中......至少不会很快。因为像 C# 和 Java 这样的语言依赖于 CLR 和 JVM。这些语言的工作方式意味着它们无法有效地加载到 ring0。

Also, the performance hit would be rather large if managed languages were employed in device drivers.

此外,如果在设备驱动程序中使用托管语言,性能损失会相当大。

回答by Can Berk Güder

First of all, note that I'm not an expert on device drivers (though I wrote a few myself back in the day), much less an expert on Java.

首先,请注意,我不是设备驱动程序方面的专家(尽管我当时自己写了一些),更不用说 Java 方面的专家了。

Let's leave the fact that writing device drivers in a high-level language is not a good idea (for performance and possibly many other reasons) aside for a moment, and answer your question.

让我们暂时将使用高级语言编写设备驱动程序不是一个好主意(出于性能和可能的许多其他原因)这一事实放在一边,然后回答您的问题。

You canwrite device drivers in almost any language, at least in theory.

您几乎可以用任何语言编写设备驱动程序,至少在理论上是这样。

However, mostdevice drivers need to do plenty of low-level stuff like handling interrupts and communicating with the OS using the OS APIs and system calls, which I believe you can't do in Java.

然而,大多数设备驱动程序需要做很多低级的事情,比如处理中断和使用操作系统 API 和系统调用与操作系统通信,我相信这在 Java 中是做不到的。

But, if your device communicates using, say, a serial port or USB, and if the OS doesn't necessarily need to be aware of the device (only your application will access the device*), then you can write the driver in any language that provides the necessary means to access the device.

但是,如果您的设备使用串行端口或 USB 进行通信,并且操作系统不一定需要知道该设备(只有您的应用程序将访问该设备*),那么您可以在任何提供访问设备的必要手段的语言。

So for example you probably can't write a SCSI card driver in Java, but you can write a driver for a proprietary control device, USB lava lamp, license dongle, etc.

例如,您可能无法用 Java 编写 SCSI 卡驱动程序,但您可以为专有控制设备、USB 熔岩灯、许可证加密狗等编写驱动程序。

* The obvious question here is, of course, does that count as a driver?

* 当然,这里显而易见的问题是,这算作驱动程序吗?

回答by TofuBeer

Writing Solaris Device Drivers in Javacovers a A RAM disk device written in Java.

用 Java 编写 Solaris 设备驱动程序涵盖了用 Java 编写的 RAM 磁盘设备。

Another one for Linux. Goes more in depth on why you might want a DD in Java as well (since some people were wondering by the looks of the other posts and comments)

另一个适用于 Linux。更深入地了解为什么您可能还需要 Java 中的 DD(因为有些人想知道其他帖子和评论的外观)

回答by starblue

You have a too narrow view of device drivers.

您对设备驱动程序的看法过于狭隘。

I have written such device drivers on top of MOST in an automotive application. A more widespread use might be drivers for USB devices if Java ever gets a decent USB library.

我已经在汽车应用中的 MOST 之上编写了这样的设备驱动程序。如果 Java 有一个像样的 USB 库,那么更广泛的用途可能是 USB 设备的驱动程序。

In these cases there is a generic low-level protocol which is handled in native code, and the Java driver handles the device specifics (data formats, state machines, ...).

在这些情况下,有一个在本机代码中处理的通用低级协议,Java 驱动程序处理设备细节(数据格式、状态机等)。

回答by TheEruditeTroglodyte

The Windows Driver Foundation (WDF) is a Microsoft API that does allow both Userand Kernelmode device drivers to be written. This is being done today, and it is now compatible with w2k and later (used to not have w2k as a supported target). There is no reason that JNI calls can't be made to do some work in the JRE . . . ( assuming that JNI is still the way to call Java from C/C++ . . . my knowledge is dated in that arena). This could be an interesting way to have high level algorithms directly munch on data from a USB pipe for something to that effect . . . cool stuff!

Windows Driver Foundation (WDF) 是一个 Microsoft API,它允许编写用户内核模式设备驱动程序。这是今天完成的,它现在与 w2k 和更高版本兼容(以前不支持 w2k 作为目标)。没有理由不能通过 JNI 调用在 JRE 中做一些工作。. . (假设 JNI 仍然是从 C/C++ 调用 Java 的方式……我的知识在那个领域已经过时了)。这可能是一种有趣的方式,让高级算法直接从 USB 管道上咀嚼数据以达到这种效果。. . 很酷的东西!