mechanical sympathy from Java view - a righteous cause?

1019 views
Skip to first unread message

Ben Cotton

unread,
Dec 20, 2013, 11:42:00 AM12/20/13
to mechanica...@googlegroups.com
First, and foremost, last thing wanted is to re-start another C/C++ vs. Java conversation.

But, I was hopeful that this forum might pep, rally, and re-motivate my belief that mechanical sympathy from the Java platform view is indeed a worth-while and righteous pursuit.

Reason I mention this is that at an (admittedly vodka fueled) holiday party last night I was overwhelmed by a pack of seasoned "C/C++ forever, just say no to Java" programmers that unanimously preached (and without any compromise) that those seeking mechanical sympathy from the Java view are fundamentally mis-directed (if not outright delusional).

They prosecuted as follows:

1.  mechanical sympathy is the pursuit of OS level/hardware/et. al. native resources to gain access to performance advantages otherwise un-available from the default development platform.
2. The Java platform purposefully denies access to OS level/hardware/et. al. native resources
3. The OS (kernel, I/O, process subsystem, system call API, hardware device drivers,etc.) are all written in C/C++ ... interfacing with these resources via C/C++ is natural and intended
4. Java platform's highest priority is WORA portability ... a necessarily OS-agnostic approach ... which, by definition, compromises its capability to fully access OS-specific mechanical resources.  
5. Java platform's non-direct access to these mechanical resources must cross a JNI bridge to C/C++ ... So, no matter how you look at it your going to wind up in C/C++ anyway.

CONCLUSION:  If you have both the capability and choice to use C/C++, why in the world wouldn't you just write your app in C/C++ in the first place?

DERIVED CONCLUSION:  pursuit of mechanical sympathy from the Java view is at conflict with itself.  Frankly, the Java platform, at its core, wants to deny you mechanical sympathy.

Though the vodka has worn off, and the prosecution has rested, I still remain a bit sympathetic to their lack of sympathy.

But I want re-engage this crowd.  Any advice for a defense re-buttal?

Happy holidays everybody,
Ben

frank.br...@gmail.com

unread,
Dec 20, 2013, 11:57:17 AM12/20/13
to mechanica...@googlegroups.com

Sorry, but I think the prosecution likely has themselves a conviction in this specific case.

Martin Thompson

unread,
Dec 20, 2013, 12:22:02 PM12/20/13
to mechanica...@googlegroups.com
This is very easy to turn into a religious war. :-)

From my personal experience the VAST MAJORITY of performance issues can be avoided with good clean design. That is, small composable methods/functions organised into a design with low coupling and high cohesion, which does not do stupid things to the underlying platform. I've seen terrible performance result from bad design in all languages.

For the limited cases of performance hot spots in a design, one must be aware of mechanical sympathy and order of algorithms. When it comes to the mechanical sympathy, some languages like C++ make it easier to communicate your intent to the machine than say Javascript. Java is somewhere in between. The focus on such areas MUST be profiler directed and not based on guesses.

When going for outright performance it is possible to squeeze out a little more with a language like C/C++, often at a huge increase in complexity, bug counts, and time to market. However the performance gap between the likes of Java and C/C++ is reducing all the time.

A fun game I often play on client engagements where such views exist is to have a bake off and see which team solve a problem fastest and get the best performance. I like to do this a few times and show that it matters more what team I'm on than which language is chosen :-) The most important point is that having good design skills and platform awareness (aka mechanical sympathy) matter more than the language. Also important is having a good network of people you can ask for help when you encounter a roadblock, which was my major reason for setting up this discussion group.

The simple way to approach such a discussions is first to define the performance goals. "Make is fast" is a crap performance goal. Once you have sensible goals based on business needs then work out the most efficient way of getting there.  Our value as programmers is to meet those goals with the simplest possible solution that can be maintained. BTW simple does not mean dumb!

Martin...

Ryan Rawson

unread,
Dec 20, 2013, 12:41:03 PM12/20/13
to mechanical-sympathy
I hope that mechanical sympathy and Java is compatible, there's an entire industry banking on it (aka the big data industry).

But the prosecution isnt entirely correct, I'll point out a few things line by line.


On Fri, Dec 20, 2013 at 8:42 AM, Ben Cotton <bendc...@gmail.com> wrote:
First, and foremost, last thing wanted is to re-start another C/C++ vs. Java conversation.

But, I was hopeful that this forum might pep, rally, and re-motivate my belief that mechanical sympathy from the Java platform view is indeed a worth-while and righteous pursuit.

Reason I mention this is that at an (admittedly vodka fueled) holiday party last night I was overwhelmed by a pack of seasoned "C/C++ forever, just say no to Java" programmers that unanimously preached (and without any compromise) that those seeking mechanical sympathy from the Java view are fundamentally mis-directed (if not outright delusional).

They prosecuted as follows:

1.  mechanical sympathy is the pursuit of OS level/hardware/et. al. native resources to gain access to performance advantages otherwise un-available from the default development platform.

To achieve performance, you want to be in alignment of the reality of the CPU/RAM/etc hardware situation.  Getting access to native kernel calls isnt the entire story.
 
2. The Java platform purposefully denies access to OS level/hardware/et. al. native resources

This use to be more so the case, but less so with nio and whatnot.  One issue is that JNI boundaries and arrays interact poorly via fully copies.  Another is the GC moves objects around (for better and worse) so you can't pass Java heap things to the Kernel.  This is fixable - with a new kernel!
 
3. The OS (kernel, I/O, process subsystem, system call API, hardware device drivers,etc.) are all written in C/C++ ... interfacing with these resources via C/C++ is natural and intended

I don't really like naturalistic arguments, mostly because they are by analogy and dont really explain anything.  Yes the friction is less, but as I pointed out, performance isn't all about calling kernel syscalls as fast as possible.

 
4. Java platform's highest priority is WORA portability ... a necessarily OS-agnostic approach ... which, by definition, compromises its capability to fully access OS-specific mechanical resources.  


This I found problematic... the stated goal of C and C++ is to be a platform neutral, portable language.  WORA too really - remember autoconf scripts that would let a project compile and run on literally a dozen unix variants with nearly as many CPU variants?

C is based on pdp11 assembler, and it's execution model no longer accurate describes how a modern super-scalar CPU works.  I'm sure Gil can talk a lot about this.  Neither is Java, but the hotspot gives it certain optimization chances C doesn't have (until LLVM, which exists exactly for this reason).  Also C has a few ugly features that prevent optimization (eg: pointer/array aliasing) which is why some folks prefer Fortran for their performant code :-)


 
5. Java platform's non-direct access to these mechanical resources must cross a JNI bridge to C/C++ ... So, no matter how you look at it your going to wind up in C/C++ anyway.

Not true, that is assuming your only method of accessing these things is via JNI libraries, but allow me to introduce you to my friend... the JVM intrinsic.

 

CONCLUSION:  If you have both the capability and choice to use C/C++, why in the world wouldn't you just write your app in C/C++ in the first place?


My personal thoughts here are, because C is too low level and error prone (memory allocation! yay!), and C++ is too complex and error prone.  Also I hate having to take a week to decide what logging platform or write one to use at the start of every C++ project.  Ditto smart pointers,  Ditto everything else.

 

DERIVED CONCLUSION:  pursuit of mechanical sympathy from the Java view is at conflict with itself.  Frankly, the Java platform, at its core, wants to deny you mechanical sympathy.

I say untrue, Java exists with a few core assumptions that makes certain forms of mechanical sympathy harder (eg: reallocating GC), but its purpose isn't to deny you system performance.  To me, performance comes from (a) CPU, (b) cache efficiency (c) RAM efficiency and (d) IO efficiency.  Each of these has a different definition of what "efficiency" means, and multiple ways of achieving it.
 

Though the vodka has worn off, and the prosecution has rested, I still remain a bit sympathetic to their lack of sympathy.

But I want re-engage this crowd.  Any advice for a defense re-buttal?

Happy holidays everybody,
Ben

--
You received this message because you are subscribed to the Google Groups "mechanical-sympathy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-symp...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

Richard Warburton

unread,
Dec 20, 2013, 12:45:47 PM12/20/13
to mechanica...@googlegroups.com
Hi,

Ignoring the bigger picture issues, which Martin Thompson has already answered very well, I think its a mistake to make the claim that ...

5. Java platform's non-direct access to these mechanical resources must cross a JNI bridge to C/C++ ... So, no matter how you look at it your going to wind up in C/C++ anyway.

You'll find that a number of methods will get converted to intrisics in hotspot.  For example you can allocate native memory without needing to cross a JNI bridge.  I'm not advocating that you should, just observing that if you want to its entirely possible.  Its also possible to access a number of OS level features, eg memory mapped files, without having Java-originating performance hits on every I/O operation.

regards,

  Richard Warburton

Simone Bordet

unread,
Dec 20, 2013, 12:49:34 PM12/20/13
to mechanica...@googlegroups.com
Hi,

On Fri, Dec 20, 2013 at 5:42 PM, Ben Cotton <bendc...@gmail.com> wrote:
> First, and foremost, last thing wanted is to re-start another C/C++ vs. Java
> conversation.
>
> But, I was hopeful that this forum might pep, rally, and re-motivate my
> belief that mechanical sympathy from the Java platform view is indeed a
> worth-while and righteous pursuit.

I think we need to define/agree what it is meant here by "mechanical sympathy".
My interpretation sticks with the "redefinition" given by Martin
Thompson, which took the definition of Jackie Stewart: know your
hardware because you'll become a better programmer (hey, I hope Martin
agrees here :)
In this light, I think that pursuing mechanical sympathy is something
you really want to look at in general, like you want to be interested
in functional programming if you have an imperative programming
background (or viceversa), or object-oriented if you have a procedural
background, etc.

> Reason I mention this is that at an (admittedly vodka fueled) holiday party
> last night I was overwhelmed by a pack of seasoned "C/C++ forever, just say
> no to Java" programmers that unanimously preached (and without any
> compromise) that those seeking mechanical sympathy from the Java view are
> fundamentally mis-directed (if not outright delusional).
>
> They prosecuted as follows:
>
> 1. mechanical sympathy is the pursuit of OS level/hardware/et. al. native
> resources to gain access to performance advantages otherwise un-available
> from the default development platform.
> 2. The Java platform purposefully denies access to OS level/hardware/et. al.
> native resources
> 3. The OS (kernel, I/O, process subsystem, system call API, hardware device
> drivers,etc.) are all written in C/C++ ... interfacing with these resources
> via C/C++ is natural and intended
> 4. Java platform's highest priority is WORA portability ... a necessarily
> OS-agnostic approach ... which, by definition, compromises its capability to
> fully access OS-specific mechanical resources.
> 5. Java platform's non-direct access to these mechanical resources must
> cross a JNI bridge to C/C++ ... So, no matter how you look at it your going
> to wind up in C/C++ anyway.
>
> CONCLUSION: If you have both the capability and choice to use C/C++, why in
> the world wouldn't you just write your app in C/C++ in the first place?

I believe this is an orthogonal problem to mechanical sympathy, and
there is tons of information online.

> DERIVED CONCLUSION: pursuit of mechanical sympathy from the Java view is at
> conflict with itself. Frankly, the Java platform, at its core, wants to
> deny you mechanical sympathy.
>
> Though the vodka has worn off, and the prosecution has rested, I still
> remain a bit sympathetic to their lack of sympathy.
>
> But I want re-engage this crowd. Any advice for a defense re-buttal?

My take is that hardware leaks abstractions up to more abstract layers.

Why there are atomic primitives in language libraries (both in Java and C++) ?
Because today every processor has atomic instructions so it's
worthwhile to have them in more abstract languages such as Java and
C++.

Why we want to have padding primitives to layout data in memory ?
Because today CPUs are multicore and effects such as false sharing do
have an important impact on performance.

Why we want arrays with power-of-two lengths to use masking instead of modulo ?
Because widespread used CPUs are known to be slower on modulo
operation than on masking.

And so forth. Hardware features leak into our code, no matter the language.

I choose Java over C++ because of the orthogonal reasons mentioned above.
Since hardware abstractions are not perfect, I need a way to control
them, both in Java and C++ (and others).

There are cases where the control of the hardware is so important and
so central that would make no sense to choose Java.
There are other cases where what is provided by Java is compelling
over C++, yet you want to be able to have some degree of control on
the hardware.

Therefore, pursuit of mechanical sympathy in Java makes sense to me.

--
Simone Bordet
http://bordet.blogspot.com
---
Finally, no matter how good the architecture and design are,
to deliver bug-free software with optimal performance and reliability,
the implementation technique must be flawless. Victoria Livschitz

frank.br...@gmail.com

unread,
Dec 20, 2013, 12:58:31 PM12/20/13
to mechanica...@googlegroups.com

There are cases where the control of the hardware is so important and 
so central that would make no sense to choose Java. 

No doubt about it.

There are other cases where what is provided by Java is compelling 
over C++, yet you want to be able to have some degree of control on 
the hardware. 

But , in the strictly mechanical sympathy sense, and with all due respect, what provided by Java is more compelling over C++?

I still think think the prosecution has met its burden  .... beyond a reasonable doubt.

Peter Lawrey

unread,
Dec 20, 2013, 1:01:16 PM12/20/13
to mechanica...@googlegroups.com
I have found that C/C++ projects tend to optimise the low level and forget the big picture.  What could be a great system in theory, often misses a number of key things because they didn't look at the end to end system and only optimise where they get the biggest gains.

For example, one system I have worked with, they have optimised the trading system very well in C/C++ and have a ~ 20 micro-seconds response time with very good stability.  A comparable system I wrote in Java about 4 years ago was about 60 micro-seconds with higher jitter.  However, they have optimised their system so much there is very little flexibility.   What is the cost of this inflexibility and narrow scope?  They  failed to take into account that the exchanges have a 800 to 2,500 micro-second response time.  So yes they optimised ~5% of the latency down to 2%, but what about the other 95%, they don't have time to investigate that nor do they have time to use the improvement which they could do. (Despite having much, much more people in the teams) So what is basic things they could have done instead?  The could have used line arbitration for market data for some exchanges, and for order placement on all exchanges.  This would speed up the round trip with the exchange by 80 - 600 micro-seconds.

In short,

The C/C++ system saved 40 micro-seconds in the trading system but miss out on between 80 - 600 micro-seconds by having a narrow view of optimisation, not where it really mattered, the exchanges. (And they had far more people to do it)

What C/C++ advocates won't talk about is how much longer or how much more man power you need to develop the same project.  This often comes with reduced flexibility, harder to refactor and innovate.

---

However, if you want to look at the low level, compare smart pointers in C++ to Java's references.  Most 64-bit JVMs use 32-bit references, and that is all that is needed, 4-bytes can address ~ 32 GB (~64 GB in Java 8).  A smart pointer consists of two 64-bit pointers, one to the reference counter which is an allocation of its own, typically a minimum of 32-bytes, and one to the actual object.  This means a smart pointer uses 16 bytes per reference and 32 bytes per object referenced. In a multi-threaded application this reference counter can be a significant overhead to maintain.  And you have to worry about circular references and bunch of other things Java handles for you.

In short, if you need the features Java provides you, the code will be as fast or faster in Java.  If you have a well understood, mature problem space (one which doesn't change too often) C/C++ is a better choice.

A thing they won't point out is that if you have a mature, well understood problem and you need to be super fast, an FPGA will beat C by a good margin.  IMHO the window between increasingly smarter FGPAs and more optimised Java systems, is getting narrower all the time.   

About ten years ago there was slightly more C++ jobs than Java jobs on jobserve.co.uk.  Now there is about 1/3 C++ compared with Java.




Regards,
   Peter.


--

Simone Bordet

unread,
Dec 20, 2013, 1:06:59 PM12/20/13
to mechanica...@googlegroups.com
Hi,

On Fri, Dec 20, 2013 at 6:58 PM, <frank.br...@gmail.com> wrote:
>> There are cases where the control of the hardware is so important and
>> so central that would make no sense to choose Java.
>
> No doubt about it.
>
>> There are other cases where what is provided by Java is compelling
>> over C++, yet you want to be able to have some degree of control on
>> the hardware.
>
> But , in the strictly mechanical sympathy sense, and with all due respect,
> what provided by Java is more compelling over C++?

If you write a microbenchmark about false sharing, C++ wins easily
since Java does not have yet public official ways of padding
(@Contended will arrive).
C++ has a lot more tools for mechanical sympathy, especially recent C++.

But I don't think this invalidates the pursuit of mechanical sympathy
in Java, because that's not the only thing I am doing with the
language.

Peter Lawrey

unread,
Dec 20, 2013, 1:21:33 PM12/20/13
to mechanica...@googlegroups.com

How does C++ handle false sharing much better? In java you just use padding. Not elegant but it works.

If you want full control you can just use Unsafe to layout native memory.

Ben Cotton

unread,
Dec 20, 2013, 1:24:20 PM12/20/13
to mechanica...@googlegroups.com

There are other cases where what is provided by Java is compelling 
over C++, yet you want to be able to have some degree of control on 
the hardware. 

But , in the strictly mechanical sympathy sense, and with all due respect, what provided by Java is more compelling over C++?

Here's one "Java is more compelling"  example for sure:  Take a look at  today's Java 7's Socket Direct Protocol capability. 

 From the comfy confines of the java.net and java.nio Socket APIs,  applications running on a Java 7 SDP configured VM can realize the full *native* Zero-Copy RDMA capability of Infiniband.  Native IB VERBs.  Directly from the physical OSI layer's NIC to the applications' Socket API view.   No walking up the OSI  Physical/Network/Internet/Transport/Session/Application stack.  Direct.  Physical--->Application.  Java 7 SDP ... mechanical sympathy at its best.

Now admittedly, it is a opulent Java environment that has IB (not ethernet) as their physical OSI network provider ... but in such settings Java hits a "more compelling over C++"  mechanical sympathy home run.

Simone Bordet

unread,
Dec 20, 2013, 1:28:55 PM12/20/13
to mechanica...@googlegroups.com
Hi,

On Fri, Dec 20, 2013 at 7:21 PM, Peter Lawrey <peter....@gmail.com> wrote:
> How does C++ handle false sharing much better? In java you just use padding.
> Not elegant but it works.

Sure. I meant to say that C++ has "primitives" while Java has not
until @Contended arrives.

> If you want full control you can just use Unsafe to layout native memory.

Sure, like manual padding, Unsafe is a bit more cumbersome to use.

To play devil's advocate here, why should I use manual padding (not
elegant) or Unsafe (cumbersome) when I can use C++ ?
I think the point is not about being _able_ to do things, both Java
and C++ can, but more about which one has the better tools.

Now I think that there is little doubt that C++ has better tools for
mechanical sympathy, but I don't think that means it is useless to
pursuit mechanical sympathy in Java.

Peter Lawrey

unread,
Dec 20, 2013, 1:36:14 PM12/20/13
to mechanica...@googlegroups.com

Why not use C++ for everything?

A: Due to the price you pay by longer time to market, higher maintenance costs, less reuse of embedded open source software. Are you willing to turn a two month Java project into a six month C++ project just to avoid manual padding?

Michael Hamrick

unread,
Dec 20, 2013, 1:39:00 PM12/20/13
to mechanica...@googlegroups.com
Martin,  if - in this game - you were on one design team advocating Java, but  the other design team  had Martin.clone() on their side (this Martin advocating C++) ... isn't it true that the C++ Martin would almost always have an advantage?

Peter Lawrey

unread,
Dec 20, 2013, 1:41:11 PM12/20/13
to mechanica...@googlegroups.com
Also playing devil's advocate, @Contended is a bit useless if you want a feature which is simple for developers to use.

Consider this class.

   class TwoCounters {
       @Contented
       final AtomicInteger counter1 = new AtomicInteger();
       @Contented
       final AtomicInteger counter2 = new AtomicInteger();
   }

Will this work as intended, No.  Just like final, @Contented applies to the references, not the objects.  The AtomicInteger have the same guarantee of being uncontended as they do of being final.

Martin Thompson

unread,
Dec 20, 2013, 1:41:24 PM12/20/13
to mechanica...@googlegroups.com
I think we need to define/agree what it is meant here by "mechanical sympathy".
My interpretation sticks with the "redefinition" given by Martin
Thompson, which took the definition of Jackie Stewart: know your
hardware because you'll become a better programmer (hey, I hope Martin
agrees here :)
In this light, I think that pursuing mechanical sympathy is something
you really want to look at in general, like you want to be interested
in functional programming if you have an imperative programming
background (or viceversa), or object-oriented if you have a procedural
background, etc.

I'm very much of the mindset that Mechanical Sympathy is all about software and hardware working together in harmony. This means writing code that works with and not against to the underlying platform. I also like to extend that platform to be the OS and Runtimes because they are as much our platform as the hardware. With an appropriate level of understanding of the underlying platform not only can we write more efficient code, we can also write code that is more robust because it is not surprised by the behaviour of that platform. Just like in motor racing, a good understanding of the safety features makes a huge difference. Take for example that fact that if you overheat your brakes then they fade or even fail. Understanding how you have configured a RAID makes a huge difference to performance and resilience, or your write patterns impact of the wear cycles for an SSD - you can do this from any language.
 
With regard to the comment on functional programming. Jackie Stewart believed there was a lot to be learned by driving in many different formula and disciples. He said he learned a lot from rallying that helped him in F1. Look at the end result, he was probably the greatest driver ever in the wet.

Having dabbled in motor racing myself it is so clear to me that the driver matters so much more than the machine. I've seen top racing drivers lap amateurs when the top drivers are in much inferior machinery. Highly specialised machinery also can have very limited use. I've had the fun of driving many types of cars on the track, and sure with some I'm faster than others. I kept advancing with such "toys" until one day I got to try a Formula 3000 race car. I thought so much power, so much grip, so much braking ability - in this I will fly. Then reality came crashing down. I did not have the skill to keep this beast right in its sweet spot. You need to drive it almost flat out otherwise the tires, brakes, and down force do not work. Needless to say I spent more time sideways and my lap times were really crap compared to what it was capable of in the right hands. 

Way too much of the C++ code I've seen looks like it has been written by someone who looks like me driving the F3000. Learning the fundamentals and constantly improving are way way more important than the machinery. Unless you are racing to be the absolute fastest, and a few actually are doing this, then we need to go as fast as necessary in an efficient and safe manner - and be enjoying it while doing it.

Martin...

Michael Hamrick

unread,
Dec 20, 2013, 1:44:12 PM12/20/13
to mechanica...@googlegroups.com

Way too much of the C++ code I've seen looks like it has been written by someone who looks like me driving the F3000. Learning the fundamentals and constantly improving are way way more important than the machinery. Unless you are racing to be the absolute fastest, and a few actually are doing this, then we need to go as fast as necessary in an efficient and safe manner - and be enjoying it while doing it.


Fabulous!  Thank you.    :-) 

Simone Bordet

unread,
Dec 20, 2013, 1:45:13 PM12/20/13
to mechanica...@googlegroups.com
Peter,

On Fri, Dec 20, 2013 at 7:36 PM, Peter Lawrey <peter....@gmail.com> wrote:
> Why not use C++ for everything?
>
> A: Due to the price you pay by longer time to market, higher maintenance
> costs, less reuse of embedded open source software. Are you willing to turn
> a two month Java project into a six month C++ project just to avoid manual
> padding?

You are pushing an open door with me :)

These are the orthogonal reasons I alluded to without detailing them
to avoid wars :)

Martin Thompson

unread,
Dec 20, 2013, 1:46:39 PM12/20/13
to mechanica...@googlegroups.com
C++ Martin can in general get a few percentage points more performance than Java Martin. However Java Martin can often complete the development a few times faster than C++ Martin.

Ben Cotton

unread,
Dec 20, 2013, 1:46:40 PM12/20/13
to mechanica...@googlegroups.com

Way too much of the C++ code I've seen looks like it has been written by someone who looks like me driving the F3000. Learning the fundamentals and constantly improving are way way more important than the machinery. Unless you are racing to be the absolute fastest, and a few actually are doing this, then we need to go as fast as necessary in an efficient and safe manner - and be enjoying it while doing it.


Fabulous!  Thank you.    :-) 

+1

Thanks Martin.  Very well said.

Howard Chu

unread,
Dec 20, 2013, 4:50:36 PM12/20/13
to mechanica...@googlegroups.com


On Friday, December 20, 2013 10:46:39 AM UTC-8, Martin Thompson wrote:
C++ Martin can in general get a few percentage points more performance than Java Martin. However Java Martin can often complete the development a few times faster than C++ Martin.

Still I think the comparison is lacking. There will be performance targets you can never hit in Java, no matter how long you spend in development.

Rajiv Kurian

unread,
Dec 20, 2013, 4:57:10 PM12/20/13
to mechanica...@googlegroups.com
I think every one here acknowledges that as it stands and if effort and manpower and expert knowledge are not an issue (rarely true in real life) C++/C can offer better absolute performance than Java. A few things where C/C++ does better than Java:

1) Access to all low level primitives that a platform might possess. This includes SIMD instructions and the pause instruction on x86 etc that have real benefit in high performance code. You have to find your own cross platform SIMD libraries that work well.
2) Structs. Every one talks about how unsafe can be used to achieve the same effect, but lets be honest unsafe is not fun to use and you end up writing C with an inferior syntax. Gil alludes to this in his "Enabling Java in Latency-Sensitive Environments" talk.  Things like padding or cache alignment are also easier done in C/C++ with the non standard__attribute__ ((aligned(#))) or __declspec( align( # ) ).
3) Very minor but I think memory mapped files are easier to use in C/C++.
4) Stack allocation is great. The JVM's escape analysis still isn't there. I am sure many will disagree with this given how heap allocation and frequent malloc-free cycles are slow. Preallocation and a good memory allocator like jemalloc helps here though. No magic solutions for cross thread malloc and free besides don't do it.

Also the amount of work put in something like GCC's optimizer shows. Hotspot maybe a marvel of engineering but GCC often does better than JITed code especially with auto vectorization.

C++ on the other hand is difficult to work with. Ignoring it's complicated syntax, the following are really painful:

1) Big projects take massive amounts of time to compile. Big companies (like Google) have entire teams set up to maintain build systems that make this less painful. This makes it difficult to get a change, compile, measure loop going.
2)  C++ lacks libraries. Some say it's because of the lack of GC. There are no established conventions on who allocates and who frees and getting libraries to work with each other is painful. Anecdotal evidence: I see questions on who is responsible for freeing all the freaking time on the libuv and concurrency kit mailing lists. The GC to some extent solves this for you. Using high performance expert written libraries are a great way to build systems that meet their performance goals. Writing a server that accepts 20k+ connections on a mediocre virtualized box is easy with libraries like Netty, Disruptor, Chronicle and Akka. It's not so trivial in C++. This leaves ample time for up front design time and also more time for the measurement/tuning phase. It also leaves time to add more features that could lead to a product being successful. That is after all the ultimate goal. For traders having more time to write and test strategies (which have short shelf times) could be more important than the 20 microseconds improvement (not free) that C++ brings to the table. I have the same argument for using Scala over Java. You lose some performance but it's easier to finish your project while business driven performance goals are still met.

If there was a project that has fixed, likely to remain stable requirements and performance is super important C++ is a great choice IMHO. Examples include a load balancer or a storage engine. Also it works great on machines with limited resources like mobile phones and embedded systems. For the rest of us mere mortals Java and other JVM languages are the perfect mix of performance and productivity. I can't stress enough how big a win it is to have libraries like Netty, Disruptor, Akka etc around to quickly build your disappearing photos application worth $2 billion. We do need to acknowledge that certain class of applications no matter how hard you try can only be done in C/C++. Many people will refuse to use even C++ on such projects and stick to C.

I am personally really excited about Rust. If you can look past it's many pointer types and complicated lifetime syntax, I think it could well be the new sweet spot. It has so many awesome features:

1) Lightweight syntax, pattern-matching, generics without the painful error messages of C++ templates but with the same performance. I would argue that most of the code is easier to read than Java thanks to the beautiful syntax.
2) Support for both 1:1 and M:N threading model. Libraries do need to be written to account for this which can be painful. Tasks also let one use non blocking IO (scheduled by the run time) with blocking syntax. This makes for really easy to write code. Again you leave some performance on the table, but doesn't matter for most people.
3) No dangling pointers, no double frees, in fact no data races. Unique pointers are checked compile time and are compiled down to raw pointers (no perf loss). The no data races is a big one especially with all the concurrent code we are writing. Again you pay a price with complicated lifetime annotations. Since there are no data races and since concurrency is done through message passing (copy less) if you allocate memory that needs to be GCed it can be done on a per task basis like Erlang. It also has RAII for releasing non memory resources.
4) Access to all the low level features of C++. This includes C++11 atomics. Easy invocation of existing native code is also a plus, though you lose all the safety guarantees. Did I mention real structs so no gymnastics needed to control layout?
5) A proper module system instead of header files. Not much here for Java developers but a big win for C++ devs.

Martin Thompson

unread,
Dec 20, 2013, 5:03:00 PM12/20/13
to mechanica...@googlegroups.com

On Friday, 20 December 2013 21:50:36 UTC, Howard Chu wrote:

On Friday, December 20, 2013 10:46:39 AM UTC-8, Martin Thompson wrote:
C++ Martin can in general get a few percentage points more performance than Java Martin. However Java Martin can often complete the development a few times faster than C++ Martin.

Still I think the comparison is lacking. There will be performance targets you can never hit in Java, no matter how long you spend in development.

You are right there are a few targets that are difficult to hit in Java. However there are very few I've not been able to work around with a bit of Unsafe and JNI, and they are getting fewer all the time as the JVM and libs advance. There are also targets that are difficult to hit in C/C++ unless using ASM or going to a FPGA.

Why is the comparison lacking.? I think it is factual. Ultimately C/C++ in the right hands can yield greater performance but with the consequence of greater time to market, higher bug count, and more complexity for all other things being equal.

Robert Frunzke

unread,
Dec 20, 2013, 5:53:36 PM12/20/13
to mechanica...@googlegroups.com
Well, I must disagree:

2)  C++ lacks libraries. Some say it's because of the lack of GC. There are no established conventions on who allocates and who frees and getting libraries to work with each other is painful. Anecdotal evidence: I see questions on who is responsible for freeing all the freaking time [..]

This is a thing every C++ developer must take responsibility for: when some library gives you some (dynamically allocated) object: who is responsible for it? Usually the context gives you a hint, and otherwise the documentation will tell you. In any case, you MUST regard it, it is essential for C++. (And in many cases objects can be stack-allocated, then it is easy...).

However, a C++ developer MUST take care of this issue, in contrast to a developer on some GC VM environment.

And the good thing about it is: there is a very clear and visible knowledge about WHO owns something at which time in processing. And this leads to a very clear and visible sense of "lifetimes of objects". Something that is unknown in (current) GC environments. Or at least it is a blurry, doubtful thing, leading to many bugs in GC environments.

Remember me, the next time you open a file, and write a try/catch clause with an additional final clause (just to close any dangling file handles) in Java ;-)

 
You lose some performance but it's easier to finish your project while business driven performance goals are still met.

Maybe. But if you trade performance against correctness, then you (or your customer) will lose some day.

It is easy to write toy-code in Java, but extremely hard to make it correct.

C++ demands much more from you, up-front, but your code will be much more correct.



Jason Koch

unread,
Dec 20, 2013, 6:05:44 PM12/20/13
to mechanica...@googlegroups.com, mechanica...@googlegroups.com

The response is that time and money and flexibility IS a factor --

If you subsitute c for any lower level primitive, and jvm for kernel or any other layer, you could equally argue that there's no point bothering with mech sympathy in such bloated environments.

Argument would go:

Why would anyone waste time on writing with c++, libc, or using the write once run anywhere kernel abstractions when you can write your own loader, machine code and device drivers for the specific hardware you own? Much more efficient!

By extension, if you write c++ you are wasting time thinking about memory layout and algorithms because if you really cared you would use machine code.

Hey just think about how much chip space is wasted on processor instructions you don't use very often! Build your own processor :)

Thanks
Jason

Robert Frunzke

unread,
Dec 20, 2013, 6:25:34 PM12/20/13
to mechanica...@googlegroups.com
Maybe, but...:


Am Samstag, 21. Dezember 2013 00:05:44 UTC+1 schrieb Jason Koch:

The response is that time and money and flexibility IS a factor --

Okey-dokey! No resistance from me.


If you subsitute c for any lower level primitive, and jvm for kernel or any other layer, you could equally argue that there's no point bothering with mech sympathy in such bloated environments.

No, C is not any lower level primitive and JVM is not the kernel! That kind of substitution is stupid, and not our topic.

 
Argument would go:

Why would anyone waste time on writing with c++, libc, or using the write once run anywhere kernel abstractions when you can write your own loader, machine code and device drivers for the specific hardware you own? Much more efficient!

By extension, if you write c++ you are wasting time thinking about memory layout and algorithms because if you really cared you would use machine code.

Read some lines below here... your assumed substitutions are rather surreal.

And your imaginary "wasted time" - is not so wasted at all, but most of the time it is essential for correct code. As I showed in my text about object lifetimes. Give "thinking about it" a try.

And comparison to "machine code" is unfair, stupid. Adding the values of two values in Java, in encapsulated integer objects, does not feel like machine code? It feels like a missing abstraction in java. But well, another topic...


Hey just think about how much chip space is wasted on processor instructions you don't use very often! Build your own processor :)

No.. whats your point here?

I am not an offender of GC VM environments at all. But I just do not like how people dismiss C++ when they have absolutely no idea of the underlying concepts, and thus in such discussions often also present how little they know about their actual GC VM environment (Java) at all. Java is not perfect, get it.

Rajiv Kurian

unread,
Dec 20, 2013, 6:29:40 PM12/20/13
to mechanica...@googlegroups.com


On Friday, December 20, 2013 2:53:36 PM UTC-8, Robert Frunzke wrote:
Well, I must disagree:

2)  C++ lacks libraries. Some say it's because of the lack of GC. There are no established conventions on who allocates and who frees and getting libraries to work with each other is painful. Anecdotal evidence: I see questions on who is responsible for freeing all the freaking time [..]

This is a thing every C++ developer must take responsibility for: when some library gives you some (dynamically allocated) object: who is responsible for it? Usually the context gives you a hint, and otherwise the documentation will tell you. In any case, you MUST regard it, it is essential for C++. (And in many cases objects can be stack-allocated, then it is easy...).

However, a C++ developer MUST take care of this issue, in contrast to a developer on some GC VM environment.

And the good thing about it is: there is a very clear and visible knowledge about WHO owns something at which time in processing. And this leads to a very clear and visible sense of "lifetimes of objects". Something that is unknown in (current) GC environments. Or at least it is a blurry, doubtful thing, leading to many bugs in GC environments.

Remember me, the next time you open a file, and write a try/catch clause with an additional final clause (just to close any dangling file handles) in Java ;-)
I typically use C++ a lot more than Java and I appreciate RAII. I am not labeling GC as a silver bullet - just observing that it helped Java to develop a rich ecosystem of high performance libraries. Rust I think again looks great in this regard. Ownership of objects is statically verified. There are no dangling pointers, no double frees, no returning a pointer to a stack allocated structure. This bugs are eliminated not with GC but with static analysis.

 
You lose some performance but it's easier to finish your project while business driven performance goals are still met.

Maybe. But if you trade performance against correctness, then you (or your customer) will lose some day.

It is easy to write toy-code in Java, but extremely hard to make it correct.

C++ demands much more from you, up-front, but your code will be much more correct.
Where did I talk about trading correctness? Could you elaborate why it is difficult to write correct code in Java or any more tougher than it is in C++? 

Rajiv Kurian

unread,
Dec 20, 2013, 6:35:37 PM12/20/13
to mechanica...@googlegroups.com


On Friday, December 20, 2013 3:29:40 PM UTC-8, Rajiv Kurian wrote:


On Friday, December 20, 2013 2:53:36 PM UTC-8, Robert Frunzke wrote:
Well, I must disagree:

2)  C++ lacks libraries. Some say it's because of the lack of GC. There are no established conventions on who allocates and who frees and getting libraries to work with each other is painful. Anecdotal evidence: I see questions on who is responsible for freeing all the freaking time [..]

This is a thing every C++ developer must take responsibility for: when some library gives you some (dynamically allocated) object: who is responsible for it? Usually the context gives you a hint, and otherwise the documentation will tell you. In any case, you MUST regard it, it is essential for C++. (And in many cases objects can be stack-allocated, then it is easy...).

However, a C++ developer MUST take care of this issue, in contrast to a developer on some GC VM environment.

And the good thing about it is: there is a very clear and visible knowledge about WHO owns something at which time in processing. And this leads to a very clear and visible sense of "lifetimes of objects". Something that is unknown in (current) GC environments. Or at least it is a blurry, doubtful thing, leading to many bugs in GC environments.

Remember me, the next time you open a file, and write a try/catch clause with an additional final clause (just to close any dangling file handles) in Java ;-)
I typically use C++ a lot more than Java and I appreciate RAII. I am not labeling GC as a silver bullet - just observing that it helped Java to develop a rich ecosystem of high performance libraries. Rust I think again looks great in this regard. Ownership of objects is statically verified. There are no dangling pointers, no double frees, no returning a pointer to a stack allocated structure. This bugs are eliminated not with GC but with static analysis.
Edit: These bugs* 

Robert Frunzke

unread,
Dec 20, 2013, 6:45:11 PM12/20/13
to mechanica...@googlegroups.com


Am Samstag, 21. Dezember 2013 00:29:40 UTC+1 schrieb Rajiv Kurian:


On Friday, December 20, 2013 2:53:36 PM UTC-8, Robert Frunzke wrote:
Well, I must disagree:

2)  C++ lacks libraries. Some say it's because of the lack of GC. There are no established conventions on who allocates and who frees and getting libraries to work with each other is painful. Anecdotal evidence: I see questions on who is responsible for freeing all the freaking time [..]

This is a thing every C++ developer must take responsibility for: when some library gives you some (dynamically allocated) object: who is responsible for it? Usually the context gives you a hint, and otherwise the documentation will tell you. In any case, you MUST regard it, it is essential for C++. (And in many cases objects can be stack-allocated, then it is easy...).

However, a C++ developer MUST take care of this issue, in contrast to a developer on some GC VM environment.

And the good thing about it is: there is a very clear and visible knowledge about WHO owns something at which time in processing. And this leads to a very clear and visible sense of "lifetimes of objects". Something that is unknown in (current) GC environments. Or at least it is a blurry, doubtful thing, leading to many bugs in GC environments.

Remember me, the next time you open a file, and write a try/catch clause with an additional final clause (just to close any dangling file handles) in Java ;-)
I typically use C++ a lot more than Java and I appreciate RAII. I am not labeling GC as a silver bullet - just observing that it helped Java to develop a rich ecosystem of high performance libraries. Rust I think again looks great in this regard. Ownership of objects is statically verified. There are no dangling pointers, no double frees, no returning a pointer to a stack allocated structure. This bugs are eliminated not with GC but with static analysis.

Okay, I can not yet imagine how static analysis could solve the problem, but I will definitely have a look at Rust!!

 
 
You lose some performance but it's easier to finish your project while business driven performance goals are still met.

Maybe. But if you trade performance against correctness, then you (or your customer) will lose some day.

It is easy to write toy-code in Java, but extremely hard to make it correct.

C++ demands much more from you, up-front, but your code will be much more correct.
Where did I talk about trading correctness? Could you elaborate why it is difficult to write correct code in Java or any more tougher than it is in C++? 

My statement was just a statement against the common statement that "c++ is just for performance".... while correctness, idioms, language features and so on are silently ignored. And the first issue seen in production java code is a lax understanding of correctness: dangling file handles, exceptions (in common error cases) that nobody can still understand (instead of plain, simple error messages to the user for common error cases), and so on.

You can write correct code in Java, but - IMHO - many people trade correctness for easy, fast-written, code.

But that is just my impression.

Robert Frunzke

unread,
Dec 20, 2013, 6:57:46 PM12/20/13
to mechanica...@googlegroups.com


There are no dangling pointers, no double frees, no returning a pointer to a stack allocated structure.

By the way: "double frees" and similar things are the issues, that Java mentors tell their pupils to make them amenable!


But, Java is not so much different. In Java, you may call on or read something from a NULL object, and get an exception.

In C++, this can happen too. But in C++ you would use stack objects and object references in situations, where an instance would actually be expected, and a plain pointer (which can be NULL) only in situations where the object actually could be NULL.

So, you would have the choice, and you would have agreements.

In Java you will not have that choice. To write correct Java, you would have to check any stupid object "ref" for being null at many stupid code points.


such are things

 

Rajiv Kurian

unread,
Dec 20, 2013, 7:10:17 PM12/20/13
to mechanica...@googlegroups.com


On Friday, December 20, 2013 3:45:11 PM UTC-8, Robert Frunzke wrote:


Am Samstag, 21. Dezember 2013 00:29:40 UTC+1 schrieb Rajiv Kurian:


On Friday, December 20, 2013 2:53:36 PM UTC-8, Robert Frunzke wrote:
Well, I must disagree:

2)  C++ lacks libraries. Some say it's because of the lack of GC. There are no established conventions on who allocates and who frees and getting libraries to work with each other is painful. Anecdotal evidence: I see questions on who is responsible for freeing all the freaking time [..]

This is a thing every C++ developer must take responsibility for: when some library gives you some (dynamically allocated) object: who is responsible for it? Usually the context gives you a hint, and otherwise the documentation will tell you. In any case, you MUST regard it, it is essential for C++. (And in many cases objects can be stack-allocated, then it is easy...).

However, a C++ developer MUST take care of this issue, in contrast to a developer on some GC VM environment.

And the good thing about it is: there is a very clear and visible knowledge about WHO owns something at which time in processing. And this leads to a very clear and visible sense of "lifetimes of objects". Something that is unknown in (current) GC environments. Or at least it is a blurry, doubtful thing, leading to many bugs in GC environments.

Remember me, the next time you open a file, and write a try/catch clause with an additional final clause (just to close any dangling file handles) in Java ;-)
I typically use C++ a lot more than Java and I appreciate RAII. I am not labeling GC as a silver bullet - just observing that it helped Java to develop a rich ecosystem of high performance libraries. Rust I think again looks great in this regard. Ownership of objects is statically verified. There are no dangling pointers, no double frees, no returning a pointer to a stack allocated structure. This bugs are eliminated not with GC but with static analysis.

Okay, I can not yet imagine how static analysis could solve the problem, but I will definitely have a look at Rust!!
Please take look at the ownership section of the tutorial and also borrowed pointers. 

 
 
You lose some performance but it's easier to finish your project while business driven performance goals are still met.

Maybe. But if you trade performance against correctness, then you (or your customer) will lose some day.

It is easy to write toy-code in Java, but extremely hard to make it correct.

C++ demands much more from you, up-front, but your code will be much more correct.
Where did I talk about trading correctness? Could you elaborate why it is difficult to write correct code in Java or any more tougher than it is in C++? 

My statement was just a statement against the common statement that "c++ is just for performance".... while correctness, idioms, language features and so on are silently ignored. And the first issue seen in production java code is a lax understanding of correctness: dangling file handles, exceptions (in common error cases) that nobody can still understand (instead of plain, simple error messages to the user for common error cases), and so on.

You can write correct code in Java, but - IMHO - many people trade correctness for easy, fast-written, code.

But that is just my impression.
Once again like I said RAII is a good pattern but the rest of what you are saying is FUD. I have very seldom heard the argument for C++ language features (besides RAII) being any good. There are too many things in the C++ language that range from minor annoyance to absolute nightmare to deal with.  The list is endless. Entire tomes have been written about the misfeatures of C++. One good one is http://yosefk.com/c++fqa/fqa.html. The only reason I am writing against C++ (a language I use almost daily) is your insistence (without any proof) that C++ lets you write more correct code and that Java users trade correctness for easy code.

Rajiv Kurian

unread,
Dec 20, 2013, 7:17:41 PM12/20/13
to mechanica...@googlegroups.com


On Friday, December 20, 2013 3:57:46 PM UTC-8, Robert Frunzke wrote:


There are no dangling pointers, no double frees, no returning a pointer to a stack allocated structure.

By the way: "double frees" and similar things are the issues, that Java mentors tell their pupils to make them amenable!


But, Java is not so much different. In Java, you may call on or read something from a NULL object, and get an exception.

In C++, this can happen too. But in C++ you would use stack objects and object references in situations, where an instance would actually be expected, and a plain pointer (which can be NULL) only in situations where the object actually could be NULL.

So, you would have the choice, and you would have agreements.

In Java you will not have that choice. To write correct Java, you would have to check any stupid object "ref" for being null at many stupid code points.
I mentioned double frees, dangling pointers etc to showcase that Rust's typing system (not Java's) prevents you from doing any of this. It still supports stack allocated objects but will not compile if you try to return a pointer to one. Just so that it's understood my post was not a  defense of Java. I merely noted just like the others that there are trade-offs to be made. Let's not get religious.

Robert Frunzke

unread,
Dec 20, 2013, 7:42:16 PM12/20/13
to mechanica...@googlegroups.com

 
You lose some performance but it's easier to finish your project while business driven performance goals are still met.

Maybe. But if you trade performance against correctness, then you (or your customer) will lose some day.

It is easy to write toy-code in Java, but extremely hard to make it correct.

C++ demands much more from you, up-front, but your code will be much more correct.
Where did I talk about trading correctness? Could you elaborate why it is difficult to write correct code in Java or any more tougher than it is in C++? 

My statement was just a statement against the common statement that "c++ is just for performance".... while correctness, idioms, language features and so on are silently ignored. And the first issue seen in production java code is a lax understanding of correctness: dangling file handles, exceptions (in common error cases) that nobody can still understand (instead of plain, simple error messages to the user for common error cases), and so on.

You can write correct code in Java, but - IMHO - many people trade correctness for easy, fast-written, code.

But that is just my impression.
Once again like I said RAII is a good pattern but the rest of what you are saying is FUD. I have very seldom heard the argument for C++ language features (besides RAII) being any good. There are too many things in the C++ language that range from minor annoyance to absolute nightmare to deal with.  The list is endless. Entire tomes have been written about the misfeatures of C++. One good one is http://yosefk.com/c++fqa/fqa.html. The only reason I am writing against C++ (a language I use almost daily) is your insistence (without any proof) that C++ lets you write more correct code and that Java users trade correctness for easy code.

You know, proofing is not easy, but let's give it a try:

C++:

struct Hello {
  void do() {
    std::cout << "Hello World" << std::endl;
  }
};

void main() {
  Hello instance;

  // .. XYZ .. here, expect a world of code doing this and that ..

  instance.do();
}


Java:

class Hello {
  public void do() {
    System.out.println("Hello World");
  }

  static void main() {
    Hello hello = new Hello();

    // .. XYZ .. here, expect a world of code doing this and that ..

    hello.do();
  }
};


The code at the comment starting with "XYZ" may not be relevant, but you do not know what it does.

In C++ you will get a guarantee - the "instance" object is still an object on the stack (though, some code may have "fucked up" anything at that actual memory location, but that would be really exceptional).

In Java you would not get any guarantee at all! Yes, no, really! You must rely on other code to behave properly in-between instantiation and call to do(). That proper behaviour - of course - is what any Java Developer expects!

But Java does not assure, that the "instance" is a valid object. C++ does so, by design, already on compilation time (no additional static analysis required to ensure that fact).

My point (and that one is religional) is, that Java Developers constantly argue about idioms and features they use, while never even trying to dilate their "feature space". It feels like "some" Java guys feel superior ... while not even knowing what exactly they are arguing about and against.

While, with C++, you can definitely shoot yourself in your foot, you can do so too in Java.

C++ has advantages, Java has advantages. Both have disadvantages.

Ryan Rawson

unread,
Dec 20, 2013, 8:20:48 PM12/20/13
to mechanica...@googlegroups.com
Micro proofs are like micro benchmarks - ultimately overly contrived and often ignore larger issues.

To address the issue, yes, references are better than potentially null pointers. The other thing you left out is the consequence of a null deref. In c and c++ a binary abort - I have not seen a segv recovery in production C/C++ code.   In Java however, you can capture and recover from a NPE, even report errors to an RPC, etc.

Finally, I agree that Java isn't safe enough.  The solution for most developers is to move to languages like Clojure and Scala, not switch back to C++.  

I think it's pretty commonly believed now that application programming in C++ - avoid at all costs.

-ryan
--

Jason Koch

unread,
Dec 20, 2013, 8:21:01 PM12/20/13
to mechanica...@googlegroups.com
To the OPs question, why bother with mechanical sympathy in Java, my response is - it is a useful abstraction even in context of its inefficiencies.

If I am to summarise - each tool has pros and cons, and we pick the level of abstraction we work at. c/c++ are still absolutely valuable tools for many problem domains where an fpga would be faster but isn't used because it is cost prohibitive or ineffective. And yet writing efficient c is still seen as important. If I can accept that writing efficient C is a worthwhile activity and simultaneously choose not to write on raw silicon, then I am making a choice about the level of abstraction to work at and what toolkit to use. Similarly, I can see an argument that there are times that writing efficient Java is worthwhile and not worth stepping into c.

Otherwise Robert, my response was to the OP's comment and not specific to yours. I have responded to yours inline.

On 21 Dec 2013, at 10:25, Robert Frunzke <robert....@gmail.com> wrote:

Maybe, but...:

Am Samstag, 21. Dezember 2013 00:05:44 UTC+1 schrieb Jason Koch:

The response is that time and money and flexibility IS a factor --

Okey-dokey! No resistance from me.


If you subsitute c for any lower level primitive, and jvm for kernel or any other layer, you could equally argue that there's no point bothering with mech sympathy in such bloated environments.

No, C is not any lower level primitive and JVM is not the kernel! That kind of substitution is stupid, and not our topic.


You are correct. The jvm is not the kernel. I suspect, possibly, you'll agree that - both the JVM and kernel are layers on which one might choose to build software instead of going to raw silicon. I make a trade in the layers of abstraction that I'm willing to work with to balance time and money, against performance requirements.

 
Argument would go:

Why would anyone waste time on writing with c++, libc, or using the write once run anywhere kernel abstractions when you can write your own loader, machine code and device drivers for the specific hardware you own? Much more efficient!

By extension, if you write c++ you are wasting time thinking about memory layout and algorithms because if you really cared you would use machine code.


Read some lines below here... your assumed substitutions are rather surreal.

And your imaginary "wasted time" - is not so wasted at all, but most of the time it is essential for correct code. As I showed in my text about object lifetimes. Give "thinking about it" a try.

Wasted time seems to be the implication of the OPs party friends - learning mech sympathy in Java is not worthwhile because you should be writing in C or whatever. Apologies I wasn't clear on that - wasted time is not with regards to use of C++. The OP comment is similar to a false dichotomy - either you want mechanical sympathy so you should write in C/C++ or you want Java so you shouldn't want to understand how the platform works. I think this is an unhelpful split - mechanical sympathy and a good understanding of the platform is useful in the context of any piece of software. My posit on wasting time is to highlight that a false dichotomy can be created to argue that you shouldn't write C++ either. Neither position is really helpful in making a good tech decision.

And comparison to "machine code" is unfair, stupid. Adding the values of two values in Java, in encapsulated integer objects, does not feel like machine code? It feels like a missing abstraction in java. But well, another topic...


This is what mech sympathy on the jvm is about. Don't use wrapped int inappropriately.


Hey just think about how much chip space is wasted on processor instructions you don't use very often! Build your own processor :)

No.. whats your point here?


c/c++ are still absolutely valuable tools for many problem domains where an fpga would be faster but cost prohibitive or ineffective. And yet writing efficient c is still important. Even down to the silicon layer, particular gates are faster or slower than others. Again, the layer of abstraction is not solely chosen for performance, and in response to OP question there are genuine reasons to want efficient code even when not working at the layer of silicon.

I am not an offender of GC VM environments at all. But I just do not like how people dismiss C++ when they have absolutely no idea of the underlying concepts, and thus in such discussions often also present how little they know about their actual GC VM environment (Java) at all. Java is not perfect, get it.

Agree with you here! Java is not perfect. I am not dismissing C++.

Rajiv Kurian

unread,
Dec 20, 2013, 8:22:01 PM12/20/13
to mechanica...@googlegroups.com
That is not a conclusive proof especially of how Java programmers trade easy code for correctness. There are instances of C++ royally screwing up everywhere on the internet. Some examples:
i) Returning pointer to a stack allocated object (C is also guilty).
ii) Throwing exceptions everywhere - you cannot throw in the destructor in C++ because your destructor might be called on a previous exception. Guess what happens on two exceptions - terminate :). Destructors don't let you return an error code either. From yosefk.com - " If you want your destructor to detect problems, make it a close function."
iii) No type safety for exceptions. Java forces you to declare exceptions and to handle them. C++ does not.
iv) Throws of polymorphic objects is weird -  a throw looks at the static type of its argument expression but catch respects inheritance :)
v) You can throw any object but  catch won't let you find out what was thrown and from where. You also don't know how many times an object that is thrown is copied.
IMHO C error handling is much better. C++ is a complete disaster.

Again I'd like to point out that modern languages like Rust will allow you to pass a stack allocated object and ensure that you cannot dereference a null pointer.



My point (and that one is religional) is, that Java Developers constantly argue about idioms and features they use, while never even trying to dilate their "feature space". It feels like "some" Java guys feel superior ... while not even knowing what exactly they are arguing about and against.

I don't think such people are on this list. Most people on this list have used C/C++.
While, with C++, you can definitely shoot yourself in your foot, you can do so too in Java.

C++ has advantages, Java has advantages. Both have disadvantages.
I think most posts here acknowledge that. I'd still argue that error handling in C++ is definitely not one of it's advantages in spite of RAII.

Robert Frunzke

unread,
Dec 20, 2013, 8:49:21 PM12/20/13
to mechanica...@googlegroups.com


Am Samstag, 21. Dezember 2013 02:20:48 UTC+1 schrieb Ryan Rawson:
Micro proofs are like micro benchmarks - ultimately overly contrived and often ignore larger issues.

To address the issue, yes, references are better than potentially null pointers. The other thing you left out is the consequence of a null deref. In c and c++ a binary abort - I have not seen a segv recovery in production C/C++ code.   In Java however, you can capture and recover from a NPE, even report errors to an RPC, etc.

Okay (a segv recovery in code would be a theoretical issue, forget it....), but my point is: this is an explicit issue, not an implicit one (that is lurking in trillions of lines of Java code to date).
 
 
Finally, I agree that Java isn't safe enough.  The solution for most developers is to move to languages like Clojure and Scala, not switch back to C++.  

Sounds like a classical strategy: "ASAP, raise to the next level before the current one crumbles" *gggg* ;-) just kidding!!!
 

I think it's pretty commonly believed now that application programming in C++ - avoid at all costs.

We could agree on many things, but not on this one!

In my world it says: "application programming in Java - avoid at all costs".


Robert Frunzke

unread,
Dec 20, 2013, 9:15:34 PM12/20/13
to mechanica...@googlegroups.com
Okay, the gory details...


 That is not a conclusive proof especially of how Java programmers trade easy code for correctness. There are instances of C++ royally screwing up everywhere on the internet. Some examples:
i) Returning pointer to a stack allocated object (C is also guilty).
 
Yes.
 
ii) Throwing exceptions everywhere - you cannot throw in the destructor in C++ because your destructor might be called on a previous exception. Guess what happens on two exceptions - terminate :). Destructors don't let you return an error code either. From yosefk.com - " If you want your destructor to detect problems, make it a close function."
 
Yes.. in practice you are right. You still could throw from a destructor, but it is one of those situations where you could shoot yourself in your feet. Or you could start re-thinking your design (in trust to the god of C++, in trust to the thought, that all of this may not be without any reason at all).

So, in a practical hot-or-not comparison between C++ and Java: What would you do in Java, if (e.g.) a file handle object inhibits its close (and though its automatic destruction) ??? What would you do, if you even just could do anything here?


iii) No type safety for exceptions. Java forces you to declare exceptions and to handle them. C++ does not.

Agreed, that one is strange.
 
iv) Throws of polymorphic objects is weird -  a throw looks at the static type of its argument expression but catch respects inheritance :)

Maybe that design was made up of the idea, that sometime someone may find a use case. But there is none (at least "there does not seem to be one"), agreed.
 
v) You can throw any object but  catch won't let you find out what was thrown and from where. You also don't know how many times an object that is thrown is copied.

Same...
 
IMHO C error handling is much better. C++ is a complete disaster.

Well, maybe. But with anything C++, YOU have the choice...

I was in doubt. And some guys at stackoverflow helped me to get "sympathy" for complete-style kind of exception handling:

http://stackoverflow.com/questions/1853243/c-do-you-really-write-exception-safe-code

The first and "accepted" answer enlightened me. And its also applicable to Java and other languages. This is how it really should be.

 
Again I'd like to point out that modern languages like Rust will allow you to pass a stack allocated object and ensure that you cannot dereference a null pointer.

My point (and that one is religional) is, that Java Developers constantly argue about idioms and features they use, while never even trying to dilate their "feature space". It feels like "some" Java guys feel superior ... while not even knowing what exactly they are arguing about and against.

I don't think such people are on this list. Most people on this list have used C/C++.

Then I am sorry!


While, with C++, you can definitely shoot yourself in your foot, you can do so too in Java.

C++ has advantages, Java has advantages. Both have disadvantages.
I think most posts here acknowledge that. I'd still argue that error handling in C++ is definitely not one of it's advantages in spite of RAII.

Okay.

But even then its not automatically an advantage of Java. From a users perspective: Whenever I have some Java program that crashes, I am totally lost. With a bit of luck I get a stacktrace (depends: on console, on gui, on log file), but usually this contains totally useless information. E.g. the trace was created some dozen lines of code after the actual error line (yeah, that is very common!!!) --- come one, you all know that stuff... you do not really want to defend that gross mess of bad code out there? Do you?

Java supports that kind of program.



Ryan Rawson

unread,
Dec 20, 2013, 9:47:36 PM12/20/13
to mechanical-sympathy
In defense of Java stacktraces, a full stack trace in the log has helped me debug a problem many a time.

I think the problem here is you just aren't experienced on the Java stack.  Yes, the stack traces are verbose, but compared to 'Program received SIGSEGV" - it's a vast improvement.  Yes I know you can debug a segv, but the reality is you won't be able to - because the problem happened on a production system you have no access to.  In Java land, users submit the log, which includes the stack trace, and it helps.  A lot. 

Once you understand how Java works, you will no longer be 'totally lost'.  You still be enlightened.  

I say this as a developer who has supported C++ and Java in production (at scale/big companies, not my third cousin's 50 hit a day website).  The Java stacktrace is a substantial upgrade from my past experience.




Robert Frunzke

unread,
Dec 20, 2013, 10:00:26 PM12/20/13
to mechanica...@googlegroups.com
Okay, I think you understood my points, and I think I understood yours too.

And let's leave it at that. For the sake of a merry christmas! :)

Robert Frunzke

unread,
Dec 20, 2013, 10:03:22 PM12/20/13
to mechanica...@googlegroups.com
Aaargh, I've read the wrong name: same christmas message goes out to Rajiv Kurian! ;-)

Rajiv Kurian

unread,
Dec 20, 2013, 10:05:32 PM12/20/13
to mechanica...@googlegroups.com


On Friday, December 20, 2013 6:15:34 PM UTC-8, Robert Frunzke wrote:
Okay, the gory details...

 That is not a conclusive proof especially of how Java programmers trade easy code for correctness. There are instances of C++ royally screwing up everywhere on the internet. Some examples:
i) Returning pointer to a stack allocated object (C is also guilty).
 
Yes.
 
ii) Throwing exceptions everywhere - you cannot throw in the destructor in C++ because your destructor might be called on a previous exception. Guess what happens on two exceptions - terminate :). Destructors don't let you return an error code either. From yosefk.com - " If you want your destructor to detect problems, make it a close function."
 
Yes.. in practice you are right. You still could throw from a destructor, but it is one of those situations where you could shoot yourself in your feet. Or you could start re-thinking your design (in trust to the god of C++, in trust to the thought, that all of this may not be without any reason at all).

So, in a practical hot-or-not comparison between C++ and Java: What would you do in Java, if (e.g.) a file handle object inhibits its close (and though its automatic destruction) ??? What would you do, if you even just could do anything here?
I would implement a close function that returns an error code that can be checked to figure out what happened and make sure I called it - C style. If a file is closed in a destructor (RAII style) and it fails, there is nothing the calling code can do. RAII is a good pattern but not a silver bullet. For extreme hardiness IMO one has to do error checking C style - at the call site with good old fashioned if statements :)


iii) No type safety for exceptions. Java forces you to declare exceptions and to handle them. C++ does not.

Agreed, that one is strange.
It's not only "strange" this leads to more correct and robust programs.
 
iv) Throws of polymorphic objects is weird -  a throw looks at the static type of its argument expression but catch respects inheritance :)

Maybe that design was made up of the idea, that sometime someone may find a use case. But there is none (at least "there does not seem to be one"), agreed.
If ifs and buts were candy and nuts... Again showing how C++ exceptions were an after thought
 
v) You can throw any object but  catch won't let you find out what was thrown and from where. You also don't know how many times an object that is thrown is copied.

Same...
 
IMHO C error handling is much better. C++ is a complete disaster.

Well, maybe. But with anything C++, YOU have the choice...

I was in doubt. And some guys at stackoverflow helped me to get "sympathy" for complete-style kind of exception handling:

http://stackoverflow.com/questions/1853243/c-do-you-really-write-exception-safe-code

The first and "accepted" answer enlightened me. And its also applicable to Java and other languages. This is how it really should be.
Seems like you agree with most of the quirks I mentioned. Let me distill the discussion since I think we are straying into a Java vs C++ argument (inevitable in such discussions). The original question asked if it is it valuable to try to apply mechanical sympathy to Java in spite of C++'s supposed advantages. My answer was yes it is. Almost every poster here agreed that C++ in the right hands is faster and has more low level features to play with. I mentioned a few points to support that assertion too. My point is that Java or other JVM languages are a great way to quickly write complex applications while still meeting quite stringent performance requirements. One of the reasons it is quicker to write code is GC. Also no one claims that GC is a silver bullet and that it frees you from managing all resources. I will claim though that since in the average application memory is 90% of resources you manage GC does lead to less code. For other resources I still prefer C style error checking (in Java and C++) instead of depending on RAII. So to summarize time to market is a big deal and Java + mechanical sympathy is a good solution but not the only one.

 
Again I'd like to point out that modern languages like Rust will allow you to pass a stack allocated object and ensure that you cannot dereference a null pointer.

My point (and that one is religional) is, that Java Developers constantly argue about idioms and features they use, while never even trying to dilate their "feature space". It feels like "some" Java guys feel superior ... while not even knowing what exactly they are arguing about and against.

I don't think such people are on this list. Most people on this list have used C/C++.

Then I am sorry!


While, with C++, you can definitely shoot yourself in your foot, you can do so too in Java.

C++ has advantages, Java has advantages. Both have disadvantages.
I think most posts here acknowledge that. I'd still argue that error handling in C++ is definitely not one of it's advantages in spite of RAII.

Okay.

But even then its not automatically an advantage of Java. From a users perspective: Whenever I have some Java program that crashes, I am totally lost. With a bit of luck I get a stacktrace (depends: on console, on gui, on log file), but usually this contains totally useless information. E.g. the trace was created some dozen lines of code after the actual error line (yeah, that is very common!!!) --- come one, you all know that stuff... you do not really want to defend that gross mess of bad code out there? Do you?
Wait what? Java stacktrace on a null pointer exception vs SIGSEGV in C++ and you think SIGSEGVs are easier to debug? Could not disagree more :)

Rajiv Kurian

unread,
Dec 20, 2013, 10:13:06 PM12/20/13
to mechanica...@googlegroups.com

Gil Tene

unread,
Dec 21, 2013, 12:34:13 AM12/21/13
to mechanica...@googlegroups.com
The language of your source code matters to mechanical sympathy in computers about as much as the language a race car driver speaks does to how fast he can get around a race course.

And theology arguments between people who are only good in C/C++ and people who are only get in Java are about as sensible as theology arguments between Hindus and Christians.  

To me, it's all machine instructions at the end. It's silly to talk about which language you write it in when the instructions that the CPU runs at the end are exactly the same. When I look at critical path code that I want to be super efficient, all care about is the generated code that actually executes, and could care less if it's generated by gcc, LLVM, or C2. I'll use whatever language best fits the things I'm trying to fit this super efficient code into, whether it's C (with goto statements) in kernel code, C++ in JVM code, or Java in libraries that lots of other people can actually use. In all cases, I try to code these fast-path things with the machine in mind, and I consider the machine to be the thing my code will be running on, in it's entirety.

The machine you need mechanical sympathy for is the one you run on, with all it's layers.

And a key thing to keep in mind is that most of your code (by volume)n should be non-critical-path code, and for that code maintain-ability, undeerstand-ability, debug-ability, and stability are dramatically more important that straight-line speed. That means that the most natural language to use is the one that your your applications and ecosystem will tend towards, and the one that provides you with the most leverage. Whether it's Python, Java, C, Scala, C++, or PHP doesn't really matter, but if you write to something with no ecosystem, you are taking on a lot of unneeded work. In 2013, writing app server libraries in C++ is just as silly as writing Java code for running Facebook games. And writing kernel modules in Scala is just as silly as writing Hadoop code in C.

To put this Java vs. C++ discussion in perspective, lets rip on some other "too abstract to know the machine" levels before we ease up and come back to reality:

- C++ programmers that think they program to the metal are kidding themselves. From a kernel programmer's point of view, C++ programs are for little children that live in little sand boxes and can't be trusted with actual access to the hardware they run on. I haven't seen much [real-world] kernel code written in C++, and user mode code is inherently separated form the hardware by an abstraction layer that takes away your code's control over whether or not it's even running, and when. Anyone that tries to make a user-mode spin loops actually work (without isolcpus or some such) runs into this one pretty fast. 

- [SMP, scheduled] Kernels are way to abstract to control hardware well with. A tight loop (with interrupts disabled) is the only way to directly control what a CPU is doing.

- Do I really need to continue? We can go into x86 instructions vs. microcode and keep going down to ECC, power management, hypervisors, and all the other things that stand between you and you actual execution.

Now that I've hopefully demonstrated the fallacy of "the machine is the user-mode interface to the Linux kernel", and given a reason to think in more generic terms like "the machine is the thing we run on, and we should understand it", Saying that virtual calls or automatic memory management create abstractions that separate you too much from the metal is no different than saying that a scheduler, virtual memory and user-mode/kernel-mode separation do the same. I'd say that Java just has a couple of more layers to the machine than user mode C/C++ have, and that being 14 steps removed or 12 steps removed from content performance transistor behavior is not a big difference.

Robert Frunzke

unread,
Dec 21, 2013, 1:23:59 AM12/21/13
to mechanica...@googlegroups.com
Okay, you got my attention...

 
[...] I'll use whatever language best fits the things I'm trying to fit this super efficient code into, whether it's C (with goto statements) in kernel code, C++ in JVM code, or Java in libraries that lots of other people can actually use. [...]

So, in your stereotyped world, C must have goto statements, C must be in kernel code and C++ in JVM code. Nice prerequisites!

 
In all cases, I try to code these fast-path things with the machine in mind, and I consider the machine to be the thing my code will be running on, in it's entirety.

Of course, you do.
 

[...] doesn't really matter, but if you write to something with no ecosystem, you are taking on a lot of unneeded work. In 2013, writing app server libraries in C++ is just as silly as writing Java code for running Facebook games. [...]

You forgot to mention, that any goal in the arts of application server framework technology was already reached, exploited and technologically exhausted.

And building up on that situation, it does not matter if you build up on concrete, silicon, paper or air - because ... ehm, well, yes, why?

 
To put this Java vs. C++ discussion in perspective, lets rip on some other "too abstract to know the machine" levels before we ease up and come back to reality:

- C++ programmers that think they program to the metal are kidding themselves. From a kernel programmer's point of view, C++ programs are for little children that live in little sand boxes and can't be trusted with actual access to the hardware they run on. I haven't seen much [real-world] kernel code written in C++, and user mode code is inherently separated form the hardware by an abstraction layer that takes away your code's control over whether or not it's even running, and when. Anyone that tries to make a user-mode spin loops actually work (without isolcpus or some such) runs into this one pretty fast. 

Please elaborate on this one!

- [SMP, scheduled] Kernels are way to abstract to control hardware well with. A tight loop (with interrupts disabled) is the only way to directly control what a CPU is doing.

Well, if you say it!
 
- Do I really need to continue? We can go into x86 instructions vs. microcode and keep going down to ECC, power management, hypervisors, and all the other things that stand between you and you actual execution.

Okay, but what is your point then???
 

Now that I've hopefully demonstrated the fallacy of "the machine is the user-mode interface to the Linux kernel", and given a reason to think in more generic terms like "the machine is the thing we run on, and we should understand it", Saying that virtual calls or automatic memory management create abstractions that separate you too much from the metal is no different than saying that a scheduler, virtual memory and user-mode/kernel-mode separation do the same. I'd say that Java just has a couple of more layers to the machine than user mode C/C++ have, and that being 14 steps removed or 12 steps removed from content performance transistor behavior is not a big difference.

Okay, I am not sure, but I think I understood. But what is your point here???


Gil Tene

unread,
Dec 21, 2013, 3:39:18 AM12/21/13
to <mechanical-sympathy@googlegroups.com>
On Dec 20, 2013, at 10:23 PM, Robert Frunzke <robert....@gmail.com> wrote:

Okay, you got my attention...

 
[...] I'll use whatever language best fits the things I'm trying to fit this super efficient code into, whether it's C (with goto statements) in kernel code, C++ in JVM code, or Java in libraries that lots of other people can actually use. [...]

So, in your stereotyped world, C must have goto statements, C must be in kernel code and C++ in JVM code. Nice prerequisites!


No stereotypes, prerequisites or limitations stated (by me) here. *I* use all three on a semi-weekly basis, and I see nothing wrong with any of them. I use each when it is the right tool for the job at hand, and I style my code by the environment it's meant to go into.

I'm a pragmatist, and I have work to do. I'm not a language evangelist, and I certainly don't try to bring Java to the kernel heathens. I don't try to use Java for kernel programming, or C for app servers. Either would be silly in this decade. I don't try to avoid gotos when they are the right and accepted way to do things in the kernel code I write (I also use vi and stick to 80 char windows and 8 space tabs for that code). I don't try to avoid C++ in it's natural idiomatic forms when coding in well established C++ environments (I use wider term windows for that). And I don't try to avoid Java (or Scala, or Python) when building reusable code pieces and libraries aimed at people who can consume them in that form (and I use IDEs for that).

In the end, they all generate machine code that looks pretty much the same for doing 1+1, or walking linked list, or reading a message. I know because I also read way too much generated machine code.

Why anyone would insist that one of these languages or idioms is the only right one to use is beyond me, but at the same time watching some of the attempts to force-use some of them in places where everyone else uses something else can be funny and sad at the same time. It can look a lot like a missionary arguing with cannibals. But It's noble work, I guess.

I've seen kernels written in Java (and in C++). I've seen app server frameworks written in C (and in C++). Both existed very briefly and probably won't be attempted again any time soon. The last time I saw someone write an HR management application in C was in the 1980s. And we are probably well past the point where a new departmental business application with a web interface will be written in C++. I know it *can*, but I can't think of why. Except for job security, but then you really should use APL.

 
In all cases, I try to code these fast-path things with the machine in mind, and I consider the machine to be the thing my code will be running on, in it's entirety.

Of course, you do.
 

[...] doesn't really matter, but if you write to something with no ecosystem, you are taking on a lot of unneeded work. In 2013, writing app server libraries in C++ is just as silly as writing Java code for running Facebook games. [...]

You forgot to mention, that any goal in the arts of application server framework technology was already reached, exploited and technologically exhausted.

And building up on that situation, it does not matter if you build up on concrete, silicon, paper or air - because ... ehm, well, yes, why?

There will be plenty of innovation ahead. And new languages to use where current ones seem right. But forging those new realities will be the job of the very few, while people who build applications right now choose the current tools that work. I predict that you'll see a lot more of the likes of Spring and Ruby on Rails and Django and Node.js come (and go?) than you would new COBOL based app server frameworks in the future.  

 
To put this Java vs. C++ discussion in perspective, lets rip on some other "too abstract to know the machine" levels before we ease up and come back to reality:

- C++ programmers that think they program to the metal are kidding themselves. From a kernel programmer's point of view, C++ programs are for little children that live in little sand boxes and can't be trusted with actual access to the hardware they run on. I haven't seen much [real-world] kernel code written in C++, and user mode code is inherently separated form the hardware by an abstraction layer that takes away your code's control over whether or not it's even running, and when. Anyone that tries to make a user-mode spin loops actually work (without isolcpus or some such) runs into this one pretty fast. 

Please elaborate on this one!

You probably don't mean to say that you think user-mode spinlocks work, or are a good idea (in the real world). The simple answers are "no they don't", and "spinlocks are things only kernels get to do without seriously breaking stuff". We can start a whole thread on that one if you want (suggested topic: "are user mode spinlock fundamentally broken?")


- [SMP, scheduled] Kernels are way to abstract to control hardware well with. A tight loop (with interrupts disabled) is the only way to directly control what a CPU is doing.

Well, if you say it!
 
- Do I really need to continue? We can go into x86 instructions vs. microcode and keep going down to ECC, power management, hypervisors, and all the other things that stand between you and you actual execution.

Okay, but what is your point then???
 

Now that I've hopefully demonstrated the fallacy of "the machine is the user-mode interface to the Linux kernel", and given a reason to think in more generic terms like "the machine is the thing we run on, and we should understand it", Saying that virtual calls or automatic memory management create abstractions that separate you too much from the metal is no different than saying that a scheduler, virtual memory and user-mode/kernel-mode separation do the same. I'd say that Java just has a couple of more layers to the machine than user mode C/C++ have, and that being 14 steps removed or 12 steps removed from content performance transistor behavior is not a big difference.

Okay, I am not sure, but I think I understood. But what is your point here???

That mechanical sympathy from a Java point of view and from a C++ point of view are very similar. Except for people who can only see one point of view.

They are both about understanding the machine you run on and getting the most out of it. Not about explaining why your blue machine is fundamentally better than the yellow machines that ignorant heretics use.




--
You received this message because you are subscribed to a topic in the Google Groups "mechanical-sympathy" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/mechanical-sympathy/6xt1URgjnZY/unsubscribe.
To unsubscribe from this group and all of its topics, send an email to mechanical-symp...@googlegroups.com.

ben.c...@alumni.rutgers.edu

unread,
Dec 21, 2013, 3:43:11 AM12/21/13
to mechanica...@googlegroups.com, mechanica...@googlegroups.com
So I just awoke from a deep slumber to answer my phone (it is. 3.40am in NYC) .

The caller just happened to be the 'lead prosecutor' from last night's party.

Me:  'hello'

Caller: 'All roads lead to Rome.  And. ... When in Rome do as the Romans.'

Me:  'u r still drunk, what the F r u talking about?'

Caller:  'Go read Gil Tene's response to your mechanical-sympathy post'

(I hang-up and start reading)

Wow.  Rings clear. An epiphany. Thank u so much Gil.

Indeed, thank you *all* for these incredibly thoughtful responses.

Defense rests.  Happy holidays.

Ben

Sent from my iPhone
--
You received this message because you are subscribed to the Google Groups "mechanical-sympathy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-symp...@googlegroups.com.

Robert Frunzke

unread,
Dec 21, 2013, 5:29:45 AM12/21/13
to mechanica...@googlegroups.com
I could agree about 90% to you, except on one thing:

I'm a pragmatist, and I have work to do. I'm not a language evangelist, and I certainly don't try to bring Java to the kernel heathens. I don't try to use Java for kernel programming, or C for app servers. Either would be silly in this decade. [...]

Okay, lets ignore that "kernel programming" topic at all! That one is rather religious, and doesn't fit into this discussion, after all!

But for app servers, why not C, nor C++? Why do you think Java is so much more suited for these purposes? This is a real question! Why?

<MyDisclaimerHereBecauseEverybodyHereAddedItToo>
Yeah, I work in many different environments, in different languages on a day-to-day basis. I gathered some experience with them. I am not a newbie.
</MyDisclaimerHereBecauseEverybodyHereAddedItToo>

With all that luggage on my bag, I still think that Java is a very bad, a very, very bad compromise. I just do not understand that spontaneous defense response, whenever comparing Java to another language - beware, I will write it now, e.g.: C++! OMG!!! I wrote it down. Oh no. C++! Yeah, C++!

> I predict that you'll see a lot more of the likes of Spring and Ruby on Rails and Django and Node.js come (and go?) than you would new COBOL based app server frameworks in the future.

A safe guess. Of course, and WHO started talking about COBOL here? That one is history.

But you tried to stash a very important thing: Node.js is implemented in C++, Ruby probably in C (I do not know exactly), and Django was AFAIK based on the JVM. I know, that is not your point.

But your point is to state, that anything but C/C++ may be used for base of app server code. You state that Java is much more well-suited to application code than C/C++. Or what?

So, why not C/C++? You know about the enormous bunch of 3rd-party code (usually packaged in libraries), that is written in C/C++ and directly accessible.

BUT you still refuse to accept that fact, even while you work with it daily.

That sounds silly! That even sounds a bit schizophrenic.

- C++ programmers that think they program to the metal are kidding themselves. From a kernel programmer's point of view, C++ programs are for little children [...]
 
Did we talk about selfish C++ kernel hackers? Really? Who throwed that topic into our discussion? Stupid guy.

 

Martin Thompson

unread,
Dec 21, 2013, 5:54:08 AM12/21/13
to mechanica...@googlegroups.com
<MyDisclaimerHereBecauseEverybodyHereAddedItToo>
Yeah, I work in many different environments, in different languages on a day-to-day basis. I gathered some experience with them. I am not a newbie.
</MyDisclaimerHereBecauseEverybodyHereAddedItToo>

With all that luggage on my bag, I still think that Java is a very bad, a very, very bad compromise. I just do not understand that spontaneous defense response, whenever comparing Java to another language - beware, I will write it now, e.g.: C++! OMG!!! I wrote it down. Oh no. C++! Yeah, C++!

I've written code in a lot of languages and found them all to have a certain utility with the exception of Javascript. I like both C++ and Java for very different reasons and each have their sweet spot. I'd never say one is better than the other without context. You have made the statement that both Java is generically bad and a very bad compromise. Can you provide context and some rational argument? Looking at the tone of your written response, it looks like spewing emotion so it is hard to see what concrete point you are making :-)

Karlis Zigurs

unread,
Dec 21, 2013, 6:20:05 AM12/21/13
to mechanica...@googlegroups.com
Most amusing discussion in spirit of the holidays season ;)

One comment I may add is that in context of mechanical sympathy this discussion should be more along the lines of C/C++ vs. JVM (not just Java itself). As Gil pointed out - in the end it's all CPU instructions anyway so what matters is how easily you can get to a high quality low level code, not the language you expressed your execution path in. And that's before taking into account hours spent with ops to ensure that the operating system and network is actually configured to be fit for the task at hand (or easily will mess up your performance with 100x the impact of the difference between GC and non-GC code would).

As for the specific example provided - If you work on a project that can justify and afford the expense (since you'll be much harder pressed to find decent quality developers - something everyone on this list should be able to sympathise with) and risks (delivery timelines and unexpected heisenbugs) to develop something as large as a modern application server - by all means, do. For most decision makers the equation would be fairly simple though - the cost of extra 6 man-months (which is really just an extra calendar month in a small-ish project team and quite an underestimate as well) is 10x the cost of just slapping an extra tin in. Not to mention the lead-times a year later when some 'small' changes need to be done and a suitable professional has to be found and brought in.

Of course C/C++/ASM or even VHDL does have their place in the stack. They do tend to congregate in very specific, relatively small, critical hot paths these days. I don't think I'd suggest to replace something written in ADA with JVM run code ether. As it stands, though, the cost-benefits ratio no longer favours them as default choice for general purpose software.

The ability for a relatively not-incompetent developer to be able to throw together a large-ish code base that is fairly standards compliant for whatever business domain it needs to exist in and, assuming he has spent some time following the discussions on this list, is working within the order of magnitude of performance that comparable hand-crafted non-GC code base would in less than couple of man-months shouldn't be under-estimated. Especially as there's a good chance that by the third month there will be ether new management or new regulations coming in and requiring a rewrite ;)

Regards,
K

--
You received this message because you are subscribed to the Google Groups "mechanical-sympathy" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mechanical-symp...@googlegroups.com.

Robert Frunzke

unread,
Dec 21, 2013, 6:21:12 AM12/21/13
to mechanica...@googlegroups.com


Am Samstag, 21. Dezember 2013 11:54:08 UTC+1 schrieb Martin Thompson:
<MyDisclaimerHereBecauseEverybodyHereAddedItToo>
Yeah, I work in many different environments, in different languages on a day-to-day basis. I gathered some experience with them. I am not a newbie.
</MyDisclaimerHereBecauseEverybodyHereAddedItToo>

With all that luggage on my bag, I still think that Java is a very bad, a very, very bad compromise. I just do not understand that spontaneous defense response, whenever comparing Java to another language - beware, I will write it now, e.g.: C++! OMG!!! I wrote it down. Oh no. C++! Yeah, C++!

I've written code in a lot of languages and found them all to have a certain utility with the exception of Javascript.

Except JS? I actually like JS ;-) But it has some fundamental cons, right...
 
I like both C++ and Java for very different reasons and each have their sweet spot. I'd never say one is better than the other without context. You have made the statement that both Java is generically bad and a very bad compromise. Can you provide context and some rational argument? Looking at the tone of your written response, it looks like spewing emotion so it is hard to see what concrete point you are making :-)

That was not my intent. Java has its pros and cons, as C++ has its pros and cons.

I just tried to be some kind of antipole to all this Java Love here ;-) You may not have noticed it, but that Java Love often seems to come in company with a rather unconscious and subjectively inspired hate to C++ and all what it is and represents.

I presented some rational arguments some posts ago.

Martin Thompson

unread,
Dec 21, 2013, 7:19:13 AM12/21/13
to mechanica...@googlegroups.com
I like both C++ and Java for very different reasons and each have their sweet spot. I'd never say one is better than the other without context. You have made the statement that both Java is generically bad and a very bad compromise. Can you provide context and some rational argument? Looking at the tone of your written response, it looks like spewing emotion so it is hard to see what concrete point you are making :-)

That was not my intent. Java has its pros and cons, as C++ has its pros and cons.

I just tried to be some kind of antipole to all this Java Love here ;-) You may not have noticed it, but that Java Love often seems to come in company with a rather unconscious and subjectively inspired hate to C++ and all what it is and represents.

I presented some rational arguments some posts ago.

I certainly do not subscribe to a blind love of Java. I come face to face with its many flaws every day. Can be simple things like lack of unsigned types or the butt ugliness of clone() and serialization through to the horrendous compromise in not reifying generics. 

However the one major issue Java has from a mechanical sympathy perspective, which I'm surprised no one brought up, and that is control over memory layout. Cache missing and contention are the biggest issues in performance.

Without more control over memory layout we can never have great collections classes in Java. We need to have what is effectively arrays of structs/objects plus the ability to inline one object into another, such as an AtomicLong into a Queue implementation with appropriate padding to prevent false sharing. This is why the likes of Gil and I are pushing hard on things like the ObjectLayout initiative. In a similar vein if escape analysis does not get the love it needs it would be great to have the ability to allocate on the stack and pass by ref or value stack allocated types. The true value of stack based allocation is not avoidance of GC, it is the fact is it totally free of any concurrent interaction with another thread and thus Amdahl is not hunting it down like all other contended approaches on the heap.

I could have similar rants on C or C++ but every language has its shortcomings.

I just tried to be some kind of antipole to all this Java Love here ;-) You may not have noticed it, but that Java Love often seems to come in company with a rather unconscious and subjectively inspired hate to C++ and all what it is and represents.

The "C++ Love" can equally come in company and in my experience with greater zealotry. ;-)

Martin...

Georges Gomes

unread,
Dec 21, 2013, 7:25:37 AM