Notifications
Clear all

Don't put this on the Stack? Well, ummm...

24 Posts
4 Users
4 Likes
2,657 Views
itsCaseyDambit
(@itscaseydambit)
Member
Joined: 4 years ago
Posts: 40
Topic starter  

Alright, sports fans, I have a question to pose, but before I do, I'd like to get better acquainted with you. In that, you may better understand the answer I'm searching for. Smoke 'em if ya' got 'em...

Back in the late 80s, when the 80-386 with a VGA monitor was the hot ticket in hardware, the speed and overall performance of your program would bear poorly if the size of the executable file (.exe) was too big. Period. Data definitions ran small, the smaller the better, and storage location mattered on the 3.5" floppy disks (brand new technology back then). Long story short, I needed smaller .exe files, so I started translating Turbo C functions into assembler language using the Turbo C IDE as my platform. Wicked.

I went into the .h files, got what I needed from their function definition (and threw away the rest), and created my pseudo C functions using: asm(assembler-code); commands throughout my C code. I tore into "conio. h" and rewrote functions like clrscr() and sooo many other, turning them all into little Assembler gems that took up such little space, my executable files ended up 1:10th their original size when using standard Turbo C commands. Some functions required far more time to develop than others, but in the end, everything ran like clockwork, and was WAY FASTER than Turbo C ever dreamed of. Thank you for the time. Now...

There's a file in the Radiohead examples (see pic) for the reliable datagram client/server with a comment that I cannot comprehend.

image

 

We understand I'm familiar with both the Assembler and C languages, and I know sure tootin' what the stack is, so, could someone please explain the comment on line 34 of the code attached. It explains:

// Dont [sic] put this on the stack:

uint8_t buf[RH_NRF24_MAX_MESSAGE_LEN];

image

Let's go over what we've got...

uint8_t is an unsigned int 8 bits long, and is 8-bits in size, even when it's compiled on a 32-bit processor.

RH_NRF24_MAX_MESSAGE_LEN equals 28, but there's an overhead that leaves a length of 24 (ref: Bill)

Let's just say we have a buffer of uint8_t elements that's RH_NRF24_MAX_MESSAGE_LEN long. fine.

When may this possibly be sent to the stack?

Why would you want to?

Or better yet, how? I know anything is possible, but, in THIS code example from Radiohead? #SMH

I wish the comment left by the coder had far more explanation than "Don't put this on the stack:."

Grrr. Comments mean more than code ever will. Comments carry concept that code can't. Please comment your code consistently.

Thank you for your time, and if anyone has a clue what this <explative> is talking about, please clue me in.


   
Quote
itsCaseyDambit
(@itscaseydambit)
Member
Joined: 4 years ago
Posts: 40
Topic starter  

Side note: once I had every function that I needed from a "???.h" file translated into asm() commands, I no longer needed to #include <???.h> that file in the compile and link, which also reduces the .exe file size down considerably.

Food for thought, that's all. Programming is an art; drink with your mind the elixir of logic gates.


   
ReplyQuote
triform
(@triform)
Member
Joined: 5 years ago
Posts: 324
 
Posted by: @itscaseydambit

Alright, sports fans, I have a question to pose, but before I do, I'd like to get better acquainted with you. In that, you may better understand the answer I'm searching for. Smoke 'em if ya' got 'em...

Back in the late 80s, when the 80-386 with a VGA monitor was the hot ticket in hardware, the speed and overall performance of your program would bear poorly if the size of the executable file (.exe) was too big. Period. Data definitions ran small, the smaller the better, and storage location mattered on the 3.5" floppy disks (brand new technology back then). Long story short, I needed smaller .exe files, so I started translating Turbo C functions into assembler language using the Turbo C IDE as my platform. Wicked.

I went into the .h files, got what I needed from their function definition (and threw away the rest), and created my pseudo C functions using: asm(assembler-code); commands throughout my C code. I tore into "conio. h" and rewrote functions like clrscr() and sooo many other, turning them all into little Assembler gems that took up such little space, my executable files ended up 1:10th their original size when using standard Turbo C commands. Some functions required far more time to develop than others, but in the end, everything ran like clockwork, and was WAY FASTER than Turbo C ever dreamed of. Thank you for the time. Now...

There's a file in the Radiohead examples (see pic) for the reliable datagram client/server with a comment that I cannot comprehend.

image

 

We understand I'm familiar with both the Assembler and C languages, and I know sure tootin' what the stack is, so, could someone please explain the comment on line 34 of the code attached. It explains:

// Dont [sic] put this on the stack:

uint8_t buf[RH_NRF24_MAX_MESSAGE_LEN];

image

Let's go over what we've got...

uint8_t is an unsigned int 8 bits long, and is 8-bits in size, even when it's compiled on a 32-bit processor.

RH_NRF24_MAX_MESSAGE_LEN equals 28, but there's an overhead that leaves a length of 24 (ref: Bill)

Let's just say we have a buffer of uint8_t elements that's RH_NRF24_MAX_MESSAGE_LEN long. fine.

When may this possibly be sent to the stack?

Why would you want to?

Or better yet, how? I know anything is possible, but, in THIS code example from Radiohead? #SMH

I wish the comment left by the coder had far more explanation than "Don't put this on the stack:."

Grrr. Comments mean more than code ever will. Comments carry concept that code can't. Please comment your code consistently.

Thank you for your time, and if anyone has a clue what this <explative> is talking about, please clue me in.

They may be stating that the array should not be passed by value and only by reference? But as we know in C/C++ you can only pass an array by Ref only (i.e. a pointer).  Not sure what they are talking about here without looking into the code and honestly I try not to look at some as they can be damage to my health 😉 

Scott

 

EDIT: I looked at the code ;).  They are saying have it on the global heap and not the functions locale memory and have it created over an over again (my guess).  The array would still be allocated outside the stack though.  They may want it created once and not in an automatic way as in a function.  


   
ReplyQuote
itsCaseyDambit
(@itscaseydambit)
Member
Joined: 4 years ago
Posts: 40
Topic starter  

Yeah, any array is automatically declared as a pointer by the compiler, as are strings. Now, find the address for the int *p and int arr[] when *p = &arr and arr[] = p.  j/k. So,

He probably wants to keep it in the PSP, which makes sense because why define it more than once? 

Still, why declare global variables in the setup() function after the Serial.begin() ran and manager.init() either succeeded or failed? He made it so neither data[] or buf[] are declared and initialized until after then.

It's beyond me, but then, I'm thinking, too, that maybe their code can damage my health.

Cheers.


   
triform reacted
ReplyQuote
triform
(@triform)
Member
Joined: 5 years ago
Posts: 324
 
Posted by: @itscaseydambit

It's beyond me, but then, I'm thinking, too, that maybe their code can damage my health.

Cheer.

Yeah.  Me no like to ready codes like that! 😉


   
ReplyQuote
itsCaseyDambit
(@itscaseydambit)
Member
Joined: 4 years ago
Posts: 40
Topic starter  

Something else I would like to point out: when I was doing all the C/Assembler code translations (that I "so arrogantly" spoke of - like I was all that AND a bag of chips), I MISSED A LOT OF PUSHES ONTO THE STACK AND POPS OFF THE TOP OF THE STACK AND REGISTERS WERE CORRUPT ALL OVER. I learned the hard way what recursive function calls do to a stack overflow when not properly managed, and I'm glad to have made the mistakes I have. 

Philosophically speaking, life is one big learning experience. Learning never ends - ever (thankfully). 

Perfect I'm not, nor try to be. I miss that personal trait by a long shot.

All I ask is a chance to better understand; I invite learning from anyone and I'm always glad to lend a hand to others.

Peace always. 🧐 


   
ReplyQuote
triform
(@triform)
Member
Joined: 5 years ago
Posts: 324
 

@itscaseydambit

I know what you mean about the stack muck-ups. I've done my fair share. In the late 80's I wrote a program switcher for DOS (as in MS). There was a lot of stack slaughtering during the devl of that code 🙂 I later did a muti-taker for it and that was a big pain.  One of the things I hate about X86 based asm is the repositioning of the SP in place of a pop.  Bothersome to my eyes 😉     


   
ReplyQuote
(@starnovice)
Member
Joined: 5 years ago
Posts: 110
 

@itscaseydambit Having been a programmer since the days of the Apple II, I certainly didn't see your posting as being arrogant.  We tend to just not mention the difficulties we had in creating a program because we assume they are understood  to exist.

Pat Wicker (Portland, OR, USA)


   
ReplyQuote
frogandtoad
(@frogandtoad)
Member
Joined: 5 years ago
Posts: 1458
 
Posted by: @itscaseydambit

Side note: once I had every function that I needed from a "???.h" file translated into asm() commands, I no longer needed to #include <???.h> that file in the compile and link, which also reduces the .exe file size down considerably.

Food for thought, that's all. Programming is an art; drink with your mind the elixir of logic gates.

If you're very space conscious, then, you can also run without the serial object and just implement the standard:

int main() {

 

  return 0;
 }

... in the Arduino IDE without the setup() and loop() functions, and implement your own.

I believe you can also remove the boot loader for more speed and space!

...also, you can look into wrapping your string literals with the "F" macro

Serial.print("F("A long string moved into flash to reduce the memory footprint"));

 


   
ReplyQuote
frogandtoad
(@frogandtoad)
Member
Joined: 5 years ago
Posts: 1458
 

@triform

Posted by: @triform

They may be stating that the array should not be passed by value and only by reference? But as we know in C/C++ you can only pass an array by Ref only (i.e. a pointer). 

A pointer is not a reference, but in C++, you can actually pass a pointer by reference 😉


   
ReplyQuote
triform
(@triform)
Member
Joined: 5 years ago
Posts: 324
 

@frogandtoad

An array is passed by a pointer. In C/C++ arrays are passed as a pointer to the first element


   
ReplyQuote
frogandtoad
(@frogandtoad)
Member
Joined: 5 years ago
Posts: 1458
 

@triform

Posted by: @triform

An array is passed by a pointer. In C/C++ arrays are passed as a pointer to the first element

Indeed, when passing an array to a function, it is said to "decay" to the first element of the array.

However, I never denied that... I just made the point that in C++, you can also pass it by reference, which you cannot do in C 🙂

In C++, a pointer is not the same as a reference.

 


   
ReplyQuote
triform
(@triform)
Member
Joined: 5 years ago
Posts: 324
 

@frogandtoad

That was never in my text.  Why add to it? I made it clear what I was saying "a pointer"  I do hate extra noise when it's not needed, it does not help I think.  Sorry.


   
ReplyQuote
(@starnovice)
Member
Joined: 5 years ago
Posts: 110
 
Posted by: @frogandtoad

In C++, a pointer is not the same as a reference.

 

OK, I'm confused, I always thought by reference was just a fancy way of saying "by ptr".  Can you clarify the difference?

Pat Wicker (Portland, OR, USA)


   
ReplyQuote
frogandtoad
(@frogandtoad)
Member
Joined: 5 years ago
Posts: 1458
 
Posted by: @triform

@frogandtoad

That was never in my text.  Why add to it? I made it clear what I was saying "a pointer"  I do hate extra noise when it's not needed, it does not help I think.  Sorry.

Posted by: @frogandtoad

Indeed, when passing an array to a function, it is said to "decay" to the first element of the array.

I think my opening statement agreed with you, no?

I was just trying to provide the correct formal wording according to ISO standard(s)... and to be absolutely correct, an array (as I said and agreed with you), "decays" to a pointer to it's first element.  However, to be technically correct, there is no such thing as being passed by pointer in either C or C++, formally you pass by value in C, and can pass by both value or reference in C++, whether it be a pointer or any other relevant object.

More than happy to go through the ISO standard on this wording should you disagree.


   
ReplyQuote
Page 1 / 2