9

Java is often praised for its amazing portability, which I presume is because of the JVM. My question is what stops C from being being compiled/interpreted/JIT'ed.., if so, C can also be write once and have it work on what ever device you have. but this is not a popular mechanism for processing a C program.

What are the disadvantages of processing C in this way, also what are the advantages of processing Java in this way and not compiling to machine code, other than the portability of course?

  • Your question has already some very good answers here: stackoverflow.com/questions/3925947/… – Doc Brown Jun 2 '15 at 17:47
  • 2
    @delnan my point is that "what stops C from being being compiled/interpreted/JIT'ed" really looses its meaning when the language may target a virtual machine that has JIT or situations where the vm will identify missing features in hardware and recompile the code to match the existing hardware (such as with OpenGL (written in C) on OSX for different graphics cards). No, you can't grab something compiled to target llvm on one machine and run it as such on another processor. But the compiled / interpreted / JIT line can be quite blurred. – user40980 Jun 2 '15 at 19:16
  • 1
    Java is often hyped for it's amazing portability. It's portable to systems where the JVM has been compiled, which is to say, systems for which the JVM (written in C) has been compiled. There is nothing that prevents handling C code in the same way, except that nobody sees enough benefit from doing it to justify the effort. – Pete Becker Jun 2 '15 at 22:06
  • 2
    I'm puzzled about this bit: "what stops C from being compiled/[...]". Uh, nothing? – Andres F. Jun 2 '15 at 23:29
  • 1
    C compilers are pretty quick these days so " make myprog.c ; myprog " will probably run faster than most interpreters. – James Anderson Jun 3 '15 at 9:24
18

C is what I would call a mid-level language. Its purpose is to serve as a "very high-level assembler," which is why it works so well as a compiler target, and why it embraces portability so well.

Historically, interpreters have typically been used with high-level languages, in the context of method calls. In its simplest form, an interpreter merely parses each keyword in the source language along with its associated tokens, and converts that into method calls and parameters. In practice, what most interpreters do is convert the source language into some intermediate representation, and it is that representation that is interpreted.

What stops C from being interpreted or Jitted? Nothing. But that's not C's raison d'être.

6

First of all, it's worth noting that Sun's JVM was written in C. C is a very popular language when portability is needed.

The C language is portable even though many C programs aren't. This is because C doesn't place as many restrictions on the programmer or make as many assumptions. If a C programmer wants his programs to be portable, he must put those restrictions upon himself.

In practice, that really isn't much more difficult than living with the restrictions Java forces on you. It's mostly a matter of being mindful of your endianness and primitive sizes, and using portable libraries like GTK+ instead of platform-specific libraries.

You could make a GTK+ target and C compiler that supported a virtual machine, even probably the JVM, and get existing code to work with very few changes. In fact, without the garbage collection, a C virtual machine would probably be much simpler. Why would you want to, though?

The reverse, compiling Java to native code, is likewise doable. That's basically what the JIT does. Why would you want to, though? I'm sure there are pet projects to do it "just because," but they are not in serious use.

5

You said:

Java is often praised for its amazing portability, which I presume is because of the JVM.

And there, within the first sentence, you are wrong. Java isn't portable because of the JVM. Java is portable, because the Java language is defined in a way that doesn't leave the implementor any leeway in how a program may behave.

As an example, Java has two types "int" (signed 32 bit integer) and "long" (signed 64 bit integer). C and C++ have "int" (signed at least 16 bit), "long" (signed at least 32 bit) and "long long" (signed at least 64 bit). That's because C is supposed to run on many different processors, and allows them to behave differently.

C could have defined fixed sizes for these types. If it had, then 36 bit processors couldn't have implemented the C language. And they can't indeed implement Java! So C allowed the language to work with a variety of different computers. It is unavoidable that this allows creation of code that is not portable. It's a matter of the language.

  • It's possible to emulate 32-bit arithmetic on a 36-bit machine ANDing the result of every operation with 0xFFFFFFFF to truncate it to 32-bits. So, these machines could implement Java, it would just be slower than if Java allowed nonet-based types. – dan04 Jun 19 '15 at 22:52
4

Java is highly portable specifically because the language targets the Java Virtual Machine, which, as the name implies, is not a real machine. Since you can implement a Virtual Machine on the architecture of many different types of real machines, a JVM-based program is highly portable.

C, on the other hand, is specifically designed to be run against real hardware, because it was created for the specific purpose of implementing an operating system, which needs full hardware access. This means that C code is not particularly portable by design, and when porting a C program from one platform to another, various parts that are specific to the target architecture will need to be rewritten to one degree or another.

  • 7
    C is highly portable. You just have to recompile on the target platform, and avoid those few bits that are specifically and intentionally not portable. – Robert Harvey Jun 2 '15 at 17:51
  • 5
    @RobertHarvey: ...such as things as fundamental as the size of various primitives? ;) – Mason Wheeler Jun 2 '15 at 17:56
  • 2
    Yes, those things. It is unfortunate that the problem exists, but the language is fully portable in every other way, and there are ways to make sure that primitive sizes work on all platforms. – Robert Harvey Jun 2 '15 at 17:57
  • 3
    @RobertHarvey: I would say C makes it possible to write portable programs, but it does not make it inherently easy. – Doc Brown Jun 2 '15 at 18:01
  • 2
    @RobertHarvey: do you want to start a religious war? ;-) My favorite portable language is Python. – Doc Brown Jun 2 '15 at 18:24
3

There actually are interpreted versions of C, but they are mostly meant to be used for quick experimentation rather than production system.

They are not commonplace, because after all, why would you suffer all the C idiosyncrasies if not to get a small, fast and static executable?

3

Theoretically both C and Java can be both compiled to native code, interpreted, or compiled to a virtual machine.

The technical reason that C is not compiled to a virtual machine, is that there is simply no standard virtual C machine.

And nobody seems to want to define a virtual C machine, or even compile to the Java virtual machine (which is perfectly possible). Probably because nobody who uses C wants to loose its unrivaled speed. Probably also because C is strongest in the open source community that can easily do portability by compilation (distribute and recompile the source and execute), so they do not feel such a need for portability of execution (distribute and execute a binary) as a closed source developer do.

1

Actually, this is done. There are major compilers which support compilation to LLVM (I know clang does, and I believe gcc does as well). That LLVM can be JIT'd just as Java code is compiled down to bytecode which is JIT'd.

However, what makes java "cross platform" as compared to C is that Java has a large runtime library which has been ported to many platforms. C explicitly does not follow this paradigm.

  • C with POSIX can be quite portable (to any POSIX system), if you code with care. – Basile Starynkevitch Jun 3 '15 at 5:53
0

There's some major differences between Java and C. Java is isolated from the operating system via the java virtual machine (JVM). The JVM abstracts the operating system away from the program. A java application might ask the JVM for a chunk of memory, and the JVM then asks the OS for that memory. There are many JVMs for different platforms / operating systems. The JVM is what allows the same java program to run on different platforms.

With C, there is no OS isolation. C programs (usually) run directly on top of the OS, making direct OS calls. This makes ties that C program to a specific operating system / platform. Any non-trivial program is going to make calls into the operating system. In addition, C programs are compiled down into machine code, which is hardware specific. A compiled C program for x86 cannot be directly run on an ARM processor.

  • 1
    Java is compiled into platform-agnostic bytecode which can be (theoretically, at least) executed by any JVM on any platform. C is compiled into assembly language for whatever CPU you are targeting (so if you're targeting the x86 architecture, the C compiler will create x86 assembler, or amd64 assembler if you're targeting that architecture, or ARM assembler, etc). Then the assembly language is turned into object files (binary assembler, really), which are linked into an executable file (several different formats, depending on the target machine). – Craig Jun 2 '15 at 20:28
  • 1
    There is nothing in the Java Language Specification that says anything about the JVM, and in fact, there are implementations of Java without the JVM. On Android, Java programs run on the Dalvik VM (now obsolete) or the Android Runtime, there are implementations of Java for the CLI, implementations that compile to ECMAScript, and implementations that compile to native code. There are C compilers which compile to the JVM. There are C compilers which compile to ECMAScript. There are C interpreters. – Jörg W Mittag Jun 2 '15 at 22:14

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.