Page 4 of 5

Re: [SOLVED] .NET vs C languages

Posted: Wed Mar 16, 2011 10:55 pm
by bnpph
Christo is the oracle of Oracle. Very good points!


I don't agree with Java using garbage collection for everything - it is inefficient more often than not. Garbage collection should be something that is optional, as many times it is much better to do without.
Calling malloc() and free() isn't especially cheap either.
It always bothers me how people write C/C++ using malloc/free as the only memory handlers. If you want to get the best performance, you really have to use some sort of pool.

Re: [SOLVED] .NET vs C languages

Posted: Wed Mar 16, 2011 11:01 pm
by TheBuzzSaw
Then why are the big game companies not flocking to Java? Because they're too brainlessly attached to C++? What're you trying to prove? The bottom line is Java lacks control afforded in C++.

Re: [SOLVED] .NET vs C languages

Posted: Wed Mar 16, 2011 11:31 pm
by Falco Girgis
christo wrote:Arguing that static compilation will not ever be completely replaced by dynamic compilation is like saying horse and cart will never be completely replaced by cars. It is technically true but despite what may have one time been seen as a neck-and-neck race, there is no competition and no debate about superior performance.
There are some glaring flaws with your metaphor.

A "car" and a "horse" are two linearly independent entities that fulfill the same need. A car is not built upon a horse. A car does not run on the same underlying architecture as a horse.

A dynamically compiled language not only runs on the same architecture as a statically compiled language, but it is built upon a statically compiled language. Java's JIT compiler is written in C. Last I heard, Microsoft's JIT compiler in the .NET framework was written in C++. You literally cannot have dynamically compiled language without a statically compiled language. Performance, ease-of-use, and any other argument you have in favor of one another aside, C# and Java both NEED C/++ to do their job. I don't believe a car requires a horse to do its job.

And there are still some glaring problems with your assumptions. I hate to use the term "you computer science majors," but I'm going to. You computer science majors seem to be forgetting some EXTREMELY important architecture that literally invalidates all of your arguments. How exactly do things like memory-mapped external hardware factor into your grand "JIT compilation global domination" schemes? The concept of a pointer literally doesn't exist within JIT compiled languages. You don't have access to memory addresses to perform low-level communication with hardware. Guess what CAN communicate with such hardware? Statically compiled C/++.

You have no direct access to things such as DMA devices for transferring data to external devices. How do you think polygons and data are submitted to your GPU in the case of video games?

You have no direct access to CPU registers to push and pop the state of the CPU onto the stack for context switching between two running processes. You have no access to translation lookaside buffers (TLBs) to implement a page table. How can you write an OS in a JIT-compiled language?

You have zero access to SIMD and vector instructions that platforms such as x86, MIPS, and many other architectures implement to speed up data-level parallel computations. "Well the JIT compiler could do that as an optimization" you say? And what about the fact that you literally cannot allocate a block of memory without 1) having metadata associated with a structure/class 2) having no idea how said structure is actually laid out in memory. These are optimizations that either cannot be performed in Java/C# or cannot be performed WELL. Do a little bit of research about data-level parallel optimizations, and you'll see that there's a good reason for C/++ reigning supreme. Here's an interesting read from the creators of the God of War series:
http://www.research.scea.com/research/p ... 8Mar03.pdf

What about the entire embedded-systems market that is geared towards low power consumption, minimalist CPU usage, and minimalist RAM usage? Do you really think you are going to see Toyota Prius's or Dishwasher's with embedded chips literally consuming 5x the power they should and 10x the RAM just to dynamically compile some simple program that would run a million times better in assembly? This market is still dominated by pure assembly programs to this day...

The argument essentially boils down to: you cannot perform any low-level assembly operations, communication with hardware, memory operation, etc in a JIT compiled language. The entire ideology that these languages were built upon was to abstract this kind of thing away from the programmer. Now I'm sure you're thinking "well what about external libraries, functions implemented by the JIT compiler, etc." That's not even an argument. Any low level access that JIT languages even do have are because of bindings/wrappings to lower level C/++ functions, where C/++ is doing the work. Look at XNA for example. It's C# sitting on a gigantic layer of C++ for the DirectX/Hardware interaction. It is far more than a glorified wrapper, yes, but it is only able to do what it does because of a gigantic base of precompiled C++.

Now lets take the argument one step further and look at why the argument for "JIT compilation completely replacing static compilation" is completely impossible with modern architectures. A processor is a finite state machine executing a series of COMPILED, BINARY instructions/opcodes. When a computer/processor boots up, it loads a series of instructions to begin executing (your bios or your operating system). These instructions are already there. Statically precompiled. It's inconceivable that a processor could load instructions (that it cannot understand) to begin dynamically compiling an OS. There would still have to be some form of statically precompiled code sitting there to tell the processor to load the JIT compiler. Once again, with a modern, assembly opcode executing CPU it is absolutely impossible to not have some form of static compilation present for dynamic compilation. Static compilation is a BUILDING block that dynamic compilation REQUIRES.

Until we have CPUs that literally decode .NET IL code or Java Bytecode in hardware (and then either execute them directly or translate them into native opcodes), it is a physical impossibility that a dynamic compilation will replace static compilation. And what if it did? What if hardware really did decode the intermediate code? Then wouldn't that intermediate code become statically compiled code, since it is directly executed and was originally compiled to IL code? It's a recursive, never-ending argument that all boils down to the fact that dynamic compilation not only requires, but is literally built upon static compilation.

"Oh, sure. There will always be those few little reasons that we will need static compilation, but they will be very few and far between." Okay, true. I agree. Then stop saying dynamic compilation will replace static compilation. The truth of the matter is that these "very few and far between reasons" that you seem to be neglecting in your higher-level computer-science-y view of the world of computing is ALL that people like lower level computer and electrical engineers working with architecture, operating systems, hardware-software integration, GPUs, external processors, or even the talented dudes WRITING your JIT compiler are concerned with. If you feel comfortable enough to say that "dynamic compilation will FULLY replace static compilation," then I feel comfortable enough stereotyping you as a typical computer scientist who is blissfully unaware of anything lower-level than your own level of abstraction.

Re: [SOLVED] .NET vs C languages

Posted: Wed Mar 16, 2011 11:32 pm
by Falco Girgis
bnpph wrote:
Calling malloc() and free() isn't especially cheap either.
It always bothers me how people write C/C++ using malloc/free as the only memory handlers. If you want to get the best performance, you really have to use some sort of pool.
Very, very true.

Re: [SOLVED] .NET vs C languages

Posted: Wed Mar 16, 2011 11:50 pm
by wtetzner
GyroVorbis wrote:
christo wrote:Arguing that static compilation will not ever be completely replaced by dynamic compilation is like saying horse and cart will never be completely replaced by cars. It is technically true but despite what may have one time been seen as a neck-and-neck race, there is no competition and no debate about superior performance.
There are some glaring flaws with your metaphor.

A "car" and a "horse" are two linearly independent entities that fulfill the same need. A car is not built upon a horse. A car does not run on the same underlying architecture as a horse.

A dynamically compiled language not only runs on the same architecture as a statically compiled language, but it is built upon a statically compiled language. Java's JIT compiler is written in C. Last I heard, Microsoft's JIT compiler in the .NET framework was written in C++. You literally cannot have dynamically compiled language without a statically compiled language. Performance, ease-of-use, and any other argument you have in favor of one another aside, C# and Java both NEED C/++ to do their job. I don't believe a car requires a horse to do its job.

...
I know you're not actually replying to my post, but I wasn't stating that VMs will replace statically compiled languages. I just wanted to address some misconceptions about Java performance.

Re: [SOLVED] .NET vs C languages

Posted: Wed Mar 16, 2011 11:51 pm
by wtetzner
GyroVorbis wrote:
bnpph wrote:
Calling malloc() and free() isn't especially cheap either.
It always bothers me how people write C/C++ using malloc/free as the only memory handlers. If you want to get the best performance, you really have to use some sort of pool.
Very, very true.
Which is basically what the JVM's garbage collector does.

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 12:54 am
by bnpph
GyroVorbis, I think you are missing the point.

Yes, JIT requires static compilation, but this does not mean that it will run slower than static code.

And as a side note, most machine code is JIT bytecode, as many x86 processors change it to some internal risc instructions, then move it all around before executing it.

Which is basically what the JVM's garbage collector does.
JVM's garbage collector is much more complex and carries much more overhead. The benefits with pools is that you can implement a specialized pool allocation function that is faster/more-efficient than malloc. Java is silly in how you only can use 1 garbage collector and everything uses it, however it is a very good implementation if you require garbage collection.

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 2:08 am
by christo
Thanks for your detailed response. I can see you've put a lot of thought into it.

Unfortunately I won't be able to address all your points. Many of which I'm not interested in disagreeing with.
GyroVorbis wrote:
christo wrote:Arguing that static compilation will not ever be completely replaced by dynamic compilation is like saying horse and cart will never be completely replaced by cars. It is technically true but despite what may have one time been seen as a neck-and-neck race, there is no competition and no debate about superior performance.
There are some glaring flaws with your metaphor.

A "car" and a "horse" are two linearly independent entities that fulfill the same need. A car is not built upon a horse. A car does not run on the same underlying architecture as a horse.

A dynamically compiled language not only runs on the same architecture as a statically compiled language, but it is built upon a statically compiled language. Java's JIT compiler is written in C. Last I heard, Microsoft's JIT compiler in the .NET framework was written in C++. You literally cannot have dynamically compiled language without a statically compiled language. Performance, ease-of-use, and any other argument you have in favor of one another aside, C# and Java both NEED C/++ to do their job. I don't believe a car requires a horse to do its job.
Nonsense. There's absolutely no need for C or C++ to implement Java. You can implement the entire Java stack in Java including native compilation. In fact a lot of early Java development, including runtimes, compilers and development environments, such as those written by OTI were written in Smalltalk, an even more dynamic runtime than Java.
GyroVorbis wrote: And there are still some glaring problems with your assumptions. I hate to use the term "you computer science majors," but I'm going to. You computer science majors seem to be forgetting some EXTREMELY important architecture that literally invalidates all of your arguments. How exactly do things like memory-mapped external hardware factor into your grand "JIT compilation global domination" schemes? The concept of a pointer literally doesn't exist within JIT compiled languages. You don't have access to memory addresses to perform low-level communication with hardware. Guess what CAN communicate with such hardware? Statically compiled C/++.
I think you're making specific arguments about Java. JIT compiled languages can support pointer arithmetic. JIT just means bundling the compiler tool chain into the executable. It doesn't require managed memory. And managed memory does not preclude pointer arithmetic. The reason modern managed runtimes and their languages don't have pointer arithmetic is because its a major source of bugs, especially security bugs.
GyroVorbis wrote: You have no direct access to things such as DMA devices for transferring data to external devices. How do you think polygons and data are submitted to your GPU in the case of video games?

You have no direct access to CPU registers to push and pop the state of the CPU onto the stack for context switching between two running processes. You have no access to translation lookaside buffers (TLBs) to implement a page table. How can you write an OS in a JIT-compiled language?
You're running through a list of low level things that are typically not bound in managed runtimes. You can make this list as long as you like, it doesn't imply that deciding how those resources are used will be done better by a human at coding time than a runtime at execution time and it does not preclude the development of languages and runtimes that expose those hardware features such that they can be manually managed when humans can do a better job.

I think you'll make faster progress if you recognise that the only thing executing is native code - in either case. I'm trying to correct your core misconception which is that there is some kind of lineage or hierarchy between static compilation and dynamic runtimes and that dynamic runtimes pay a tax as they execute by "going down the levels". You conclude that C++, having fewer of these "levels" (and assembly having fewer again) is therefore faster. Your premise is incorrect, so your conclusion is not supported by your reasoning.
GyroVorbis wrote: Now lets take the argument one step further and look at why the argument for "JIT compilation completely replacing static compilation" is completely impossible with modern architectures. A processor is a finite state machine executing a series of COMPILED, BINARY instructions/opcodes. When a computer/processor boots up, it loads a series of instructions to begin executing (your bios or your operating system). These instructions are already there. Statically precompiled. It's inconceivable that a processor could load instructions (that it cannot understand) to begin dynamically compiling an OS. There would still have to be some form of statically precompiled code sitting there to tell the processor to load the JIT compiler. Once again, with a modern, assembly opcode executing CPU it is absolutely impossible to not have some form of static compilation present for dynamic compilation. Static compilation is a BUILDING block that dynamic compilation REQUIRES.
It's very interesting that you use the phrase "modern architectures". Increasingly, modern laptop, desktop and server CPUs in the post Pentium era actually do exactly what you say they do not. Even in the case of an assembly program written and executed without an operating system, just so we can be nice and clean and get away from these confusing notions of "c++ wrappers" as you call them and compilers, the CPU does not execute a series of instructions as they have been compiled. Way back in the before time, this is how CPUs worked but these days things are much more complex.

When the preconditions are met, these CPUs can reorder instructions, unroll loops and start executing branches before the test condition has been executed. In essence the modern CPU is doing EXACTLY what a modern managed runtime tries to do. They try to optimise the code that was written by the programmer using information about the current execution state. There are some differences about what can be done but when combining increasingly wide multicore dies with increasing numbers of levels of cache, very long pipelines, hyperthreading etc. it all amounts to the same thing. The computer knows better than the programmer.
GyroVorbis wrote: Until we have CPUs that literally decode .NET IL code or Java Bytecode in hardware (and then either execute them directly or translate them into native opcodes), it is a physical impossibility that a dynamic compilation will replace static compilation.
These CPUs *have* already been developed back in the 90s (e.g. JavaStation) but having such CPUs is not sufficient to ensure faster execution (as you would no doubt know). What's interesting is that they are not necessary either.

If you or I were to implement a Java VM this weekend, we would interpret the bytecode. This is how the first runtimes were written because it's much easier to implement. However, on modern VMs such as Hotspot, the .NET CLR, the Visualworks Smalltalk VM and the V8 JavaScript VM (3 out of 4 developed by the same team in Denmark over the past 20 years) this simple interpreted mode is not how they work. IL and Java bytecode are compiled into native code multiple times with different optimisations (this can depend on VM config). IL/bytecode is basically a more convenient source format, it's literally an Intermediate form for the code before it is recompiled to native.
GyroVorbis wrote: And what if it did? What if hardware really did decode the intermediate code? Then wouldn't that intermediate code become statically compiled code, since it is directly executed and was originally compiled to IL code? It's a recursive, never-ending argument that all boils down to the fact that dynamic compilation not only requires, but is literally built upon static compilation.
I think the strongest form of your argument is that static compilation is a special case of dynamic compilation where the compilation is only done once and done without the benefit of for any execution time data. Only in that sense can you say that dynamic compilation is built upon static compilation. Is this your point or am I misunderstanding?
GyroVorbis wrote: "Oh, sure. There will always be those few little reasons that we will need static compilation, but they will be very few and far between." Okay, true. I agree. Then stop saying dynamic compilation will replace static compilation. The truth of the matter is that these "very few and far between reasons" that you seem to be neglecting in your higher-level computer-science-y view of the world of computing is ALL that people like lower level computer and electrical engineers working with architecture, operating systems, hardware-software integration, GPUs, external processors, or even the talented dudes WRITING your JIT compiler are concerned with. If you feel comfortable enough to say that "dynamic compilation will FULLY replace static compilation," then I feel comfortable enough stereotyping you as a typical computer scientist who is blissfully unaware of anything lower-level than your own level of abstraction.
You're putting quite alot of words in my mouth here. It's not helping that you keep using quotes around your own words to debate with a stereotype of me.

Saying that JITs have to be written in static languages is like saying compilers have to be written in assembly. It's just not true. It happens in many cases because of a bootstrap benefit that has more to do with other features of the language rather than that they are statically compiled.

I'll gladly write as large as you like that C++ is currently faster than Java because of a lot of the things you have written, but I'd like to correct a number of things just in case you're interested in reaching mutual understanding.

1. I'm not saying that Java will replace C++ completely or that Java or the current generation of dynamic runtimes will replace the current static compilation tool chains completely.

2. I'm comparing static vs dynamic compilation. If you don't have parity in the millions of other important features, such as hardware bindings, then you're in danger of mixing up unrelated effects when you compare different stacks. Garbage collection is not required for JIT. All the hardware bindings you were talking about are necessary in order for the dynamic runtime to optimise for them. Java/.NET and C++ are different in many ways, not just the static compilation and dynamic compilation axis.

3. I'm not defending Java for game development. The decision to use a language/stack/toolchain should be based on a range of things that are important to the project. C++ is a fine choice for your project! Perhaps it's optimal.

4. Static compilation provides superior performance within a particular envelope of factors. Perhaps this is where we can agree. If the hardware architecture has a primitive tool chain and nobody has developed advanced dynamic recompiling runtimes on them, then there is no choice but to use static compilation. It's a lot of work to develop a JIT. It's like comparing the job of racing a horse against a box full of Ferrari parts. If you can't get hold of a car then a horse is great.

5. Similarly the compiler contains a memory and a CPU overhead which is not in all cases outweighed by the benefits brought by runtime optimisations. This is your point, however I think you overstate it. Java runs in Blu Ray players, TVs, credit-card sized form factors. Having said that, I can imagine just as many microcontrollers and small CPUs that wouldn't support Java. I would argue that this doesn't mean no dynamic compilation runtime could run on it, but I do agree there will be certain cases where hardware limitations will prefer static compilation because that's work the target machine doesn't have to do.

Mind you, those machines are becoming more and more marginal. Phones and tablets are already multicore and plenty capable of managed runtimes. Look at Android. If you want to write code for washing machines I think you can probably avoid managed runtimes and JIT compilation. This is where the horse comes into its own.

Now imagine writing your own JIT. Dirty low down hacker style (I aint no CS major!). Here's your JIT debut:

Imagine your C++ project. Imagine you link a compiler into it and all the source code. Imagine you ship the source code, the compiler and a wrapper script. All without the user knowing. When the user runs the game, it randomly chooses a set of compiler options, compiles and executes that code, keeping some metrics about framerates or whatever. Then after running for 10 minutes, the program recompiles itself with different options, logs different metrics and keeps doing this until it finds the optimal set of options that provide the best framerate. Somehow you manage to hide all this from the user using "clever hacking tricks" like scheduling the work to occur when the user is looking at the menu screen or whatever. Is this crazy? Hell yeah! But it shows that you could get better performance from dynamic compilation. Now imagine the user upgrades their CPU the next week and the optimal settings are different. When you wrote the code you didn't know what would run best on their new CPU because it didn't exist then. It's brand new! But now your game runs faster than it would have because it chooses the compilation options that are optimal for that user situation. What's really cool is that when that user's little brother plays the optimal compiler options are different because the little brother never goes past level 3 in the game where the hellish FP ops are done because of all the 3d sound modelling you have on that level.

Does anyone ship their games like this? No. Why? Cost/benefit ratio. A million other reasons. Does this mean it's incorrect? No. If you think this is too theoretical, then at least admit that it is true as long as the compiler in the executable is capable of utilising optimal (according to your own metrics, e.g. framerate) compilation techniques that are local to both the target architecture AND the set of currently executing code paths. Acknowledge that these things cannot possibly be known ahead of time (statically).

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 3:23 am
by christo
I know I've subjected you to a huge wall of text already but JavaOS is an operating system (legacy as of 2006) that is written in Java (including device drivers):

http://en.wikipedia.org/wiki/JavaOS

Also, I happen to know that AMD and Intel have been specifically optimising their hardware performance to support and benefit JIT compiler stacks like Java/JVM. I don't have a reference for this and I'm not aware that it has been published (probably). If you believe me, it's more evidence that the proposed primacy of static compilation is not a universal axiom, just an accidental historical fact.

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 3:42 am
by christo
TheBuzzSaw wrote:Then why are the big game companies not flocking to Java? Because they're too brainlessly attached to C++? What're you trying to prove? The bottom line is Java lacks control afforded in C++.
Many big game companies are flocking to iOS, Flash and other managed runtimes but you're oversimplifying things. I'm not arguing Java is better than C++ for game companies. I'm only arguing that in the future, static compilation is ultimately going to prove less performant than dynamic compilation in the vast majority of cases.

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 4:11 am
by MrDeathNote
wtetzner wrote: It also annoys me when people say that the Java garbage collector is slow. Java's garbage collector is extremely efficient.
For the record when I said that the Java and C# GC is slow I mean't in memory intensive applications and only because I've tested it. I tested C# with XNA on the PC against a similar C++ app and the garbage collector tanked the frame rate because it was so busy chewing on itself. I generally never use java for games so the gc in java doesn't annoy me nearly as much.

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 9:15 am
by GroundUpEngine
N64vSNES wrote:
MrDeathNote wrote:
dandymcgee wrote:
GyroVorbis wrote:I'm sorry, but Java, C#, and JIT compiled languages are never going to fully replace C/++, just as C/++ will never (and cannot possibly) completely replace assembly.

I have no doubt that Java/C# will continue to become more popular for a portion of the market than C/++ (as they already have), but replace? You aren't ever going to see a JIT compiled language catching on with embedded platforms, drivers, operating systems, or anything of the like. People said the same thing about C++ "completely" replacing C. Most drivers and OSs to this day are STILL written in C (not even C++).

Until JIT compilers literally run in hardware, I cannot foresee, C, C++, or assembly ever not having a place in the market, and I believe that saying they will be "replaced" is neglecting a large portion of the market geared towards low-level development and software-hardware integration.
Well said.
+1
+2
+3 ;)

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 11:02 am
by N64vSNES
These high level V low level wars are so entertaining :lol:

All I'm saying on this is that you simply can't predict the future.

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 6:02 pm
by Aleios
GroundUpEngine wrote:
N64vSNES wrote:
MrDeathNote wrote:
dandymcgee wrote:
GyroVorbis wrote:I'm sorry, but Java, C#, and JIT compiled languages are never going to fully replace C/++, just as C/++ will never (and cannot possibly) completely replace assembly.

I have no doubt that Java/C# will continue to become more popular for a portion of the market than C/++ (as they already have), but replace? You aren't ever going to see a JIT compiled language catching on with embedded platforms, drivers, operating systems, or anything of the like. People said the same thing about C++ "completely" replacing C. Most drivers and OSs to this day are STILL written in C (not even C++).

Until JIT compilers literally run in hardware, I cannot foresee, C, C++, or assembly ever not having a place in the market, and I believe that saying they will be "replaced" is neglecting a large portion of the market geared towards low-level development and software-hardware integration.
Well said.
+1
+2
+3 ;)
+4 Gyro makes an excellent point

Re: [SOLVED] .NET vs C languages

Posted: Thu Mar 17, 2011 6:16 pm
by Ginto8
N64vSNES wrote:These high level V low level wars are so entertaining :lol:

All I'm saying on this is that you simply can't predict the future.
yes, except that a software-based VM by definition is incapable of running faster than actual statically compiled code.