Jump to content
jkroby

preprocs math optimization

Recommended Posts

Hi,

i startin try to optimize library IRremote from energia section NEC.

I removed memory usage and change timer_a function, all ok, there is a macro:

 

#define USECPERTICK (4/16) //freq. 16Mhz divisor 4
#define TOLERANCE 25  // percent tolerance in measurements
#define LTOL (1.0 - TOLERANCE/100.)
#define UTOL (1.0 + TOLERANCE/100.)

#define TICKS_LOW(us) (int) (((us)*LTOL/USECPERTICK))
#define TICKS_HIGH(us) (int) (((us)*UTOL/USECPERTICK + 1))

define MATCH(measured,desired) (measured >= TICKS_LOW(desired) && measured <= TICKS_HIGH(desired))

 

where desired is an integer constant, i have found this code. i have changed USECPERTICK because i use timer as capture with clock divisor of 4.

 

The code size is about 4000 bytes. about 600 bytes other part of previous program.

i think it is not possible, the program is very simply, so i use this macro:

 

#define MATCH(measured,desired) (measured >= desired##_A && measured <= desired##_B)

 

where i create 2 new constant by hand

 

#define NEC_HDR_MARK     9000
#define NEC_HDR_MARK_A  27000
#define NEC_HDR_MARK_B 180000
 

so the preprocs use the _A and _B variant.

 

size reduced to ~ 750 bytes.

in the last years i use Perl, java, javascript for the 98% of my programs but i remember:

The preprocs exec math operation, when it can, and put a numeric constant.

There is some flag to use?

What needs for? in Perl there isn't preprocs ok, but in C there is so what it needs if it is converted in code?!

i can wrote all in c code and then manually optimized.

 

Roberto.

Share this post


Link to post
Share on other sites

You use lines like

#define TICKS_LOW(us) (int) (((us)*LTOL/USECPERTICK))

but the C standard will evaluate us/LTOL first and then multiply by USECPERTICK. If you use a line like this

#define TICKS_LOW(us) (int) (((us)*(LTOL/USECPERTICK)))

the division will be done in the precompiler. Still, since this is a floating point number, the multiplication will Reilly in a floating point number. Of you want to force the compiler to do an integer multiplication, do

#define TICKS_LOW(us) (int) (((us)*(int)(LTOL/USECPERTICK)))

Share this post


Link to post
Share on other sites

Better,

but not enought, the size is reduced to 3273 bytes (3723 before), with constants 741 bytes.

 

In theory the preprocessor had to convert all he can in constants, because all values are constants, but it does'n do it.

 

Robero.

Share this post


Link to post
Share on other sites

Are you suite all are constants? Only of all values are known at compile time the evaluations will be done by the preprocessor. Also, try getting rid of any floating point number, floats take a huge amount of code, since the processor does not natively support them. I would be much more able to point things out if you posted your whole code.

Share this post


Link to post
Share on other sites

the usage is:

 

MATCH(TIME,NEC_BIT_MARK)

 

for instance, where time is the variable and NEC_BIT_MARK is a constant

 

#define NEC_BIT_MARK      560


i know, floating point is big, but it should be a way for calculating a constant not by hand, not wrote by me, i found the code and i use it.

My idea is only optimize the code for integrate in a non development program.

i use another way with all constant by hand.

 

Roberto.

Share this post


Link to post
Share on other sites

Hi,

found solution, if someone is interested.

 

                                       4.0 need for float calculation no (4)

#define USECPERTICK (4.0/16) //freq. 16Mhz divisor 4
#define TOLERANCE 25  // percent tolerance in measurements
#define LTOL (1.0 - TOLERANCE/100.)
#define UTOL (1.0 + TOLERANCE/100.)

 

                                         (unsigned int) need for no runtime conversion
#define TICKS_LOW(us) (unsigned int) (((us)*LTOL/USECPERTICK))
#define TICKS_HIGH(us) (unsigned int) (((us)*UTOL/USECPERTICK + 1))
 

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×