This page is a mirror of Tepples' nesdev forum mirror (URL TBD).
Last updated on Oct-18-2019 Download

Cc65 programming question #define

Cc65 programming question #define
by on (#178513)
Is this good programming style?

Let's say I wanted to reuse a set of global variables in multiple functions, but I don't want to call them arg1, arg2, etc within the function.

Can I just use #define to give arg1 a fancy new name to use just for that function? Like...

#define X_velocity arg1

And then in another function use the same generic global variable with a different #define

#define frame_count arg1

Does that seem like a good idea? Assuming I'm not nesting these two functions together, and using the same global, or is this style just potentially error prone?

EDIT, and if you're wondering why I just don't use the C stack and/or local variables... they seem to be significantly slower than global variables.
Re: Cc65 programming question #define
by on (#178514)
I think with a better compiler than CC65 it would be bad style, or in C++, but for this application I think it's probably good.

You can #undef at the end of scope to remove the alias too, so you don't have a bunch of extra defines lying around (and can reuse names later).

With an optimizing compiler I would just create a new variable inside the scope reading the argument (e.g. char X_velocity = arg1;), and usually the optimization pass ends up eliminating it, but in CC65 you don't have such a luxury, so you kind of do have to do it by hand.

C++ too added & types to create aliases by reference, which would also obviate the need for this kind of thing, but you don't get this in C, unfortunately.


Also maybe worth noting that you can indent a #define, and place them inside of functions if you like. They have no internal concept of scope, but you can still place them "visually" within a scope to help.
Code:
void boing()
{
   #define spring arg1
   
   if(spring)
      sproing();
   else
      sprocket();
   
   return;
   #undef spring
}
Re: Cc65 programming question #define
by on (#178537)
I think it's alright to do this.

In fact, I do this for my opponent variables. I have a struct that contains arrays of variables that are there for the opponents. There are some common variables, like X and Y. But there is also a bunch of variables that are just called value 1, value 2, value 3 etc.
For each opponent type, I redefine these variables with macros:
#define GoonCurrentWalkingSpeed Value1


But yes, it might also be error prone if you didn't know what you're doing. I.e. you need to be sure that functions are not nested among each other because otherwise, you might get a whole bunch of strange errors.