Author Topic: Why does ARM mbed rely on C++? Is C++ the future?  (Read 29547 times)

0 Members and 1 Guest are viewing this topic.

Offline bson

  • Supporter
  • ****
  • Posts: 2265
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #150 on: March 30, 2018, 08:31:50 pm »
Things like virtual functions are not much slower than a function call through a pointer offset / indirection, which is usually fast.
More importantly though, often when you implement a virtual method you're not always calling it through the base class, so the compiler can frequently know exactly which function you're calling and doesn't have to go through the vtable.  In many cases the use of the virtual method is only for specific uses, such as collecting statistics, diagnostics, plumbing during standup, or teardown of more complex structures.  Things that aren't performance critical but have great functional benefits (like clean layering; my personal philosophy is specialization and static link time resolution inside layers, while using vectored polymorphism between layers - unless there is a very specific reason to do otherwise).  As a more specific example, you may have a bunch of things, like TCP, UDP, USB, and UARTs offering things that are a Connection abstract base class.  But in most cases, such as inside TCP, it's a TCPEndpoint or such, not the abstract base class.  For performance you specialize around a specific class (specialization being a template class); for non-performance you use the abstract Connection.  (Note that a template class that operates on a specific type that implements a specific set of methods, and specializes for it, can itself implement a virtual base class - and hence encapsulate the performance-critical pieces.)

While tables of function pointers are common in C (this is of course why C++ has virtual methods, since it fundamentally embodies good, common C practices) the language itself has no type formalism to express it, meaning the compiler has a much harder time figuring out what's what and hence deducing if you're actually calling the virtual method or some specific type's implementation of it.  For example:

Code: [Select]
{
    // A is a B
    A a;

    ((B&)a).foo();
}

This casts a to a B and calls a virtual method foo().   But the compiler knows a is really an A and that what's called is really A::foo(), so can omit the vtable indirection.  It just becomes part of resolving constant expressions.  A C compiler would in most cases find this impossible to figure out.  (There are exceptions.)
« Last Edit: March 30, 2018, 08:59:23 pm by bson »
 

Offline andyturk

  • Frequent Contributor
  • **
  • Posts: 895
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #151 on: March 30, 2018, 09:43:26 pm »
A C compiler would in most cases find this impossible to figure out.  (There are exceptions.)

To wit: LTO, Devirtualization, and Virtual Tables

The template specialization technique sounds interesting, although I personally might not want to go that route without first identifying a performance problem via measurement. "Premature optimization is the root of all evil" and all that.
 

Offline NorthGuy

  • Super Contributor
  • ***
  • Posts: 3137
  • Country: ca
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #152 on: March 30, 2018, 10:31:12 pm »
Efficient design is simple. You take your time in the beginning to simplify things. Then you spend less money on the hardware, less time on the software development, and finally you get something which is cheaper and much easier to work with.
Time = money so your method isn't efficient by definition if you start by taking time.

Not at all. Thinking upfront saves you much more time in the future.

Thinking doesn't mean spending lots of time creating super-fast algorithms where you don't need them. It also doesn't mean creating the detailed design, drawing flowcharts and all that. It, sure as hell, doesn't mean using Agile rules. Thinking means inventing the design which brings you the biggest benefit.

My initial statement was that people tend to go for lowest cost hardware and then ending up needing to do a lot of optimisation to make the software fit on the hardware. This either means missing the deadline or releasing a half baked product.

Yes, and other people use expensive hardware without any real need for it.

Both cases are examples of doing before thinking. Selecting hardware which is not suitable for your project is a very bad mistake, which is very difficult to fix. But going for the most expensive (or most popular) hardware is not going to help. This will not shorten your development time. And you can get in troubles even with the most expensive hardware.

« Last Edit: March 31, 2018, 12:44:50 am by NorthGuy »
 

Offline C

  • Super Contributor
  • ***
  • Posts: 1346
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #153 on: March 31, 2018, 01:49:58 am »

Sorry for not explaining better.
Some is like trying to tell a 2D world person about a 3D world.
There are many things in different languages that are great.

Each option in a language can make it harder for compiler writer.
 So from the compiler writer view, fewer things and fewer options are good.

Think there would be few fighting for assembly over C.
That is just a step.
As I have said, it's all the little things that add up, the good & the bad.
A lot of the good compilers have not been open source or have no source. This leads to few good examples to follow.

As the language gets higher level and still needing low level real world access, you get to a point where you need a simple editor that does all but code generation parts of compiler.
When editor gets this smart, having different things defined in different places in source is no longer a problem.
To work better with an ADA language program, you need an editor that understands more then the source format of ADA. Less then this becomes more of a burden on programmer. C puts huge load on programmer, ADA puts finding a burden on programmer.

The compilers for the net framework have removed a lot from inside the compiler and put it in the framework.
With so much in framework you gain more constant actions for all.

Need to think of how much productive is loss by not using a higher level language in a good environment to create source code. 

The reverse side is that other then C and possibly C++ you are moving to a language with fewer using that language in embedded world.

There is a few options that are not great where you use other language to create C or C++.
But if you have access to source for these it gets some better.

You have tools that for example setup chip pins for you, but I think you will find no or few that can read source and show pin use.

So 5upercircuits
Arm had C & C++, any thing else would be time and money.

They did do a little to help other languages. But part of this is self serving as it also can help Arm.

Some have said how great Turbo pascal was, That was a huge step down from the Pascal I used in my day job.

Threads like this have existed for a very very long time.
With all kinds of reasons to not change.

 

Offline westfw

  • Super Contributor
  • ***
  • Posts: 4196
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #154 on: April 01, 2018, 12:32:33 am »
There are things that terrify me about modern programming languages.  I've recently taken a couple of Python classes.  Python is pretty neat, and it's one of those languages where you spend more time looking for libraries that have already been written than you do writing new code (or so it seems.)   That's not so bad...

But what it actually DOES is so ... opaque!  I mean, take this little factorial example:

Code: [Select]
>>> prod =  1
>>> for i in range(2,40):
...   prod *= i
...   print(i, prod)
...
2 2
3 6
4 24
5 120
  :
10 3628800
11 39916800
12 479001600
13 6227020800
 --- Oh, that's cool.  It didn't overflow at 32bits.  Uses 64bit integers, I guess!
14 87178291200
15 1307674368000
   :
28 304888344611713860501504000000
29 8841761993739701954543616000000
 --- No, wait.  This is more than 64bits.  Did the nice efficient integers I thought I was using become BIGNUMs?
 ---  Were they ALWAYS bignums?  How slow is this going, anyway?   What do I want to do if I want it to go faster?
37 13763753091226345046315979581580902400000000
38 523022617466601111760007224100074291200000000
39 20397882081197443358640281739902897356800000000

Similarly, people use "dictionaries" like arrays, only indexed by, say, strings.   colorvalue["blue"] instead of colorvalue[eColor_Blue], and it's almost physically painful to think about how that must work.

I feel like if I wanted to write Python professionally, I'd get mired in studying the internals until I understood the relative efficiencies.  Sorta like those interpreted BASIC experts with the "Don't use comments except on lines that are never executed, and be sure to use short variable names!" rules.  Ugh.

(and I can't help but noticed that if I have a list of files, each of which has a list of "things", each of which has some associated values, which I want to write using json, that my life is easier if I just do:
Code: [Select]
a = {"foo.txt":{"one":1, "two":2, "three":3}, "bar.txt":{"one":10, "two":20, "three":30}}instead of wrapping a sensible object/structure around it.  Sigh.)
 

Offline C

  • Super Contributor
  • ***
  • Posts: 1346
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #155 on: April 01, 2018, 02:21:15 am »

bignums

Big integers is most often a limit of the language and compiler.
All the 8-bit processors have the ability to do big integers.
For most you have an ADD instruction & ADD with carry.
A big number is just two or three arrays with a member size that these instructions can work on.

In addition dymanic size bignumbers are no big deal at low level. Pascal stores strings as sturcture/array of Length followed string. As the string can contain any byte value, this is storage of integers up to 255*8 bit numbers or 2040 bit integer.

As to the Blue
Smart programmer could store the Blue in a B-tree and get a binary number that is then stored in the list to be searched. A second B-tree for binary number back to text
Would not take much of list to make this faster & use less space.

Higher level that is understood gives compiler & interpreter writers options.

A good language should have a bit type and all integer bit sizes. In addition it should have the concept of a binary decimal point.  A lot of hardware is actually a ratio device, talking ADC, DAC & PWM and the bit values match with binary to right of decimal point.
You should note that Burr Brown which was well known for its ADC's & DAC's had left justified bit field .



 

 

Offline technix

  • Super Contributor
  • ***
  • Posts: 3507
  • Country: cn
  • From Shanghai With Love
    • My Untitled Blog
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #156 on: April 01, 2018, 05:49:03 am »
There are things that terrify me about modern programming languages.  I've recently taken a couple of Python classes.  Python is pretty neat, and it's one of those languages where you spend more time looking for libraries that have already been written than you do writing new code (or so it seems.)   That's not so bad...

But what it actually DOES is so ... opaque!  I mean, take this little factorial example:

Code: [Select]
>>> prod =  1
>>> for i in range(2,40):
...   prod *= i
...   print(i, prod)
...
2 2
3 6
4 24
5 120
  :
10 3628800
11 39916800
12 479001600
13 6227020800
 --- Oh, that's cool.  It didn't overflow at 32bits.  Uses 64bit integers, I guess!
14 87178291200
15 1307674368000
   :
28 304888344611713860501504000000
29 8841761993739701954543616000000
 --- No, wait.  This is more than 64bits.  Did the nice efficient integers I thought I was using become BIGNUMs?
 ---  Were they ALWAYS bignums?  How slow is this going, anyway?   What do I want to do if I want it to go faster?
37 13763753091226345046315979581580902400000000
38 523022617466601111760007224100074291200000000
39 20397882081197443358640281739902897356800000000

Similarly, people use "dictionaries" like arrays, only indexed by, say, strings.   colorvalue["blue"] instead of colorvalue[eColor_Blue], and it's almost physically painful to think about how that must work.

I feel like if I wanted to write Python professionally, I'd get mired in studying the internals until I understood the relative efficiencies.  Sorta like those interpreted BASIC experts with the "Don't use comments except on lines that are never executed, and be sure to use short variable names!" rules.  Ugh.

(and I can't help but noticed that if I have a list of files, each of which has a list of "things", each of which has some associated values, which I want to write using json, that my life is easier if I just do:
Code: [Select]
a = {"foo.txt":{"one":1, "two":2, "three":3}, "bar.txt":{"one":10, "two":20, "three":30}}instead of wrapping a sensible object/structure around it.  Sigh.)
There is very likely some heuristics in the runtime to determine when to use what. Python seem to have good efficiency overall.
 

Offline westfw

  • Super Contributor
  • ***
  • Posts: 4196
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #157 on: April 01, 2018, 09:43:27 am »
Quote
For most you have an ADD instruction & ADD with carry. ...
In addition dynamic size bignumbers are no big deal at low level.

Tell me about the relative performance of floats vs bignums on a Cortex M0?  I mean, factorials probably means probability calculations, right?   So I'll likely be dividing and multiplying as well as adding.  And it's not so much that it's HARD, but that it's a "surprise."  My supposedly quicker integer calculations now involve dynamic memory allocation, and counted loop code (just for addition), and don't really have any idea how expensive 4.0/factorial(52) is going to be in either cycles or memory.  Pretty clearly I should have used floats from the beginning, but "it worked fine in the test code on my PC - these microcontrollers are just really slow, I guess...  Can we get a faster chip?"
 

Offline C

  • Super Contributor
  • ***
  • Posts: 1346
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #158 on: April 01, 2018, 01:18:32 pm »

westfw
Did the factorials program crash?
The other choices lose something to gain something.

The big thing is higher level gives the compiler writer choices on how to get job done.
Loops become easy for CPU in the down to Zero form
 
Having choice lets you the programmer state problem at higher level and lets compiler do the same.
You can write simple to understand code at high level.
The compiler could have factorials process change based on size, No fancy IF statements needed, CPU has the overflow bit in status register.

Then is your dynamic memory allocation really dynamic allocation really dynamic?  Lower level code forces ti to be so. A higher level can do better.

With the right access some things become easy to describe.
Back in the day, I did dynamic swap of things often.

Think of starting new to programming and one of the first computers you see is one that gets dynamic patches & extensions while running the program.
This is not all that hard to do.




 

 

Offline NorthGuy

  • Super Contributor
  • ***
  • Posts: 3137
  • Country: ca
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #159 on: April 01, 2018, 02:45:56 pm »
Quote
For most you have an ADD instruction & ADD with carry. ...
In addition dynamic size bignumbers are no big deal at low level.

Tell me about the relative performance of floats vs bignums on a Cortex M0?  I mean, factorials probably means probability calculations, right?   So I'll likely be dividing and multiplying as well as adding.  And it's not so much that it's HARD, but that it's a "surprise."  My supposedly quicker integer calculations now involve dynamic memory allocation, and counted loop code (just for addition), and don't really have any idea how expensive 4.0/factorial(52) is going to be in either cycles or memory.  Pretty clearly I should have used floats from the beginning, but "it worked fine in the test code on my PC - these microcontrollers are just really slow, I guess...  Can we get a faster chip?"

How many factorials can you possibly calculate before the overflow? Not that many I guess. Thus, build a table with the pre-calculated factorials. Will be the fastest you can get.

If you always need division, pre-calculate inversed values, trim to desired precision and convert to floats - it'll be even faster and more compact.
 

Offline andyturk

  • Frequent Contributor
  • **
  • Posts: 895
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #160 on: April 01, 2018, 05:01:21 pm »
The big thing is higher level gives the compiler writer choices on how to get job done.
That's a seriously magic compiler to be able to figure out from the text of the program itself, when bignums are needed or when fixed precision numbers will do the job.
 

Offline C

  • Super Contributor
  • ***
  • Posts: 1346
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #161 on: April 01, 2018, 05:25:00 pm »
The big thing is higher level gives the compiler writer choices on how to get job done.
That's a seriously magic compiler to be able to figure out from the text of the program itself, when bignums are needed or when fixed precision numbers will do the job.

The magic is the simple CPU carry bit in the status register.
When adding two binary numbers, the max is one bit larger then what you started with.
When adding two unsigned byte values the max is a 9-bit value. When CPU get's the 9th bit it sets the carry bit in status register.
So with CPU knowing what size to add it's simple.



 

Offline andyturk

  • Frequent Contributor
  • **
  • Posts: 895
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #162 on: April 01, 2018, 06:05:41 pm »
The magic is the simple CPU carry bit in the status register.
I thought you were talking about what a compiler can do (not what can be done runtime).
 

Offline C

  • Super Contributor
  • ***
  • Posts: 1346
  • Country: us
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #163 on: April 01, 2018, 07:26:52 pm »

The compiler builds the code.
The compiler is what limits access to CPU.
The language puts limits on compiler.

It is really not that hard to have variable bit size integers in language.
I think every 8-bit CPU has larger then default size capability for integers.
Less then CPU size is just using bit masks.

Doing a good job in compiler for integers pays back in other areas also.
How many smaller then byte size fields are used in a program?

The net result is an easer to read program that compiler has more options to make faster.

Does not take much for what you call a program to act like an operating system. This can be done at high level with proper compiler, often not even needing a language change or a very minor one.

As I have said, the compiler I used was pascal based.
It could compile programs or modules.
A system programming switch let you treat a module like data while still keeping most pascal rules and error checks in tact.
To select a custom printer driver was just loading & linking a module. This was all done in my program.
A group of modules could become overlays with little more work.
Threads took a little more work to share the code. as with out system, my program had to maintain many stacks.

The smarter the compiler the less assembly is needed. It just keeps adding, better compiler can do more.
The compiler created it's self and compilers and interpreters for other languages & many different OS's.
That module capability gave easy access to many code generators.

The hard part is coding a compiler to create the newer version of compiler & then cleaning up compiler source for new foundation.

Think of C, how many C rules change for all sizes of integers. Do the rules change when your select statement uses a few bits of a var?
What could the compiler hide with out needing a language change?
Just a little change lets you have arrays that range from integer to integer and not 0 to integer-1

It all adds up.







 

Offline Korken

  • Regular Contributor
  • *
  • Posts: 84
  • Country: se
Re: Why does ARM mbed rely on C++? Is C++ the future?
« Reply #164 on: April 02, 2018, 02:52:22 pm »
It's quite interesting to see that there are a lot of pros and cons when it comes to C++, so I though I would share a few things I use when developing in C++ for embedded (and more specifically ARM Cortex-M).
The important thing is to use libraries that solve real problems, not use things just for the sake of using it.

1. State Machine Language: https://github.com/boost-experimental/sml
SML is a DSL (domain specific language) where you specify a state machine, and it generates optimized code for it.
I am using it in all my current embedded projects as soon as I need a state machine, and it comes from 2 very important features:
- There is a tool to convert the code you write for the state machine to a block diagram. This has saved me a lot of times.
- I have tried and cannot beat the state machine generated in execution speed, amazingly fast.

Thanks to it being generated at compile time, extra knowledge can be embedded in the DSL with allows for optimizations the compiler cannot see.
And this is one of the things that really is useful in embedded, as we as embedded engineers have a lot of domain specific knowledge that we put to use.
In the case of Template Metaprogramming, almost all of this knowledge and optimizations can be embedded into the DSL being created.

2. CRECT (an event based scheduler computed at compile time): https://github.com/korken89/crect
I am authoring an RTOS (if you can call it that) which generates an Stack Resource Policy scheduler for your system at compile time.
After generating the connections between resources and jobs, the scheduler is mapped to the NVIC of the Cortex-M MCUs, making it extremely fast and efficient.
I would recommend the interested to check the README in the link.
CRECT uses a DSL to describe which jobs can take which resources, that in the allows it go guarantee deadlock and data race free execution (if not using resources outside the resource system).
I presented this system at the emBO++ conference in March (embedded C++ conference) however the video is not online yet sadly.
There I started a dare, if anyone could make a scheduler that is faster - as it uses the NVIC to make context switches manual code cannot beat it.
A pleasant side-effect is that it is very easy to get sleep into the system, as when all event have been handled one can sleep (there is no code in main).

3. Extra evening material
There is a person call Odin Holmes which does a lot of talks on embedded and C++, and the systems being created.
I would really recommend people to watch his talks and get inspiration: https://www.youtube.com/playlist?list=PL85B7uUiTlCFXO_XL_2x1tlr7B8Lg9NFp
For those who want to see the future of special function register abstraction can have a look at kvasir::bit.
 


Share me

Digg  Facebook  SlashDot  Delicious  Technorati  Twitter  Google  Yahoo
Smf