NOTICE: The Processors Wiki will End-of-Life on January 15, 2021. It is recommended to download any files or other content you may need that are hosted on processors.wiki.ti.com. The site is now set to read only.

Automatically Remove Unused Constant Variables

From Texas Instruments Wiki
Jump to: navigation, search

Introduction[edit]

This article describes a C macro which automatically removes the constant variables that are not used. If that is not interesting enough, consider that this macro makes use of several unusual techniques you might find useful elsewhere, including:

  • how to stringify macro arguments
  • relying on the compiler to concatenate (smoosh together) adjacent quoted strings
  • multiple line macros
  • multiple line asm() statements
  • subsections
  • conditional linking
  • pragmas, and how to generate them from macros

The Macro[edit]

Here is a helper macro, followed by the main macro ...

<syntaxhighlight lang="c">

  1. define PRAGMA(x) _Pragma(#x)
  1. define REMOVE_UNUSED_CONSTANT(var) \
  PRAGMA(DATA_SECTION(var, ".const:" #var))    \
  asm(" .sect \".const:" #var "\"\n"           \
      " .clink")

</syntaxhighlight>

Here is how to use it ...

<syntaxhighlight lang="c"> const int one_const = 1; const int two_const = 2;

REMOVE_UNUSED_CONSTANT(one_const); // removed if not used REMOVE_UNUSED_CONSTANT(two_const); // removed if not used </syntaxhighlight>

Limitations and Caveats[edit]

  • Does not work for C++. Such a macro can probably be written, though it would not be quite as simple.
  • Invoke the macro only at the end of the source file. While it is likely to be OK when invoked elsewhere, this avoids possible problems described below in #The asm() Part.

How Does It Do That?[edit]

Overview[edit]

The pragma part of the macro places the constant variable in a section named ".const:variable name". The asm() part of the macro marks that section with the directive ".clink". That stands for conditional linking. Sections so marked are removed by the linker if it finds that the section is never used, i.e. there are no references to that variable.

Multiple Line Macros[edit]

Note how all the lines in the macro end with "\", save the last one. It is an old rule of C that #define macros must all be on one source line. The "\" syntax tells the compiler to pretend the next line was written on the current line. As you can see, you can do this repeatedly, which allows you to format a complex macro for readability.

The Pragma Part[edit]

The pragma syntax is mostly explained in Pragmas You Can Understand, particularly the VAR_IN_SECTION macro. There are two additional twists here: subsections and concatenation of string constants.

Subsections[edit]

First, subsections. The variable is placed in a section all by itself. The subsection ".const:variable name" does this. By being a subsection of .const, one of the usual sections generated by the compiler, it will be combined into the rest of .const should the linker not remove it. Even so, marking this subsection with .clink means the linker can remove it without affecting any other part of .const.

Form the Section Name with Smooshing[edit]

What does the syntax ".const:" #var do? Note there is nothing but space between the " and #. Well, from Pragmas You Can Understand, you already know that #var means that macro argument will be replaced and converted to a quoted string, also known as stringifying the macro argument. So, that means the second argument to the DATA_SECTION pragma will be ".const:" "variable" . When the C compiler sees two constant strings like that, with nothing but space between them, it concatenates them. That is, it smooshes them together as if you had written ".const:variable". And, of course, that is exactly the name of the section needed.

The asm() Part[edit]

An asm() statement is a way to inject a bit of assembly code into C compiler output. Using asm() statements is largely frowned upon, and rightly so. There are many ways to get into trouble. That said, there is little to worry about here. An asm() statement, used at file scope, which only emits assembler directives, is fairly safe. One warning: To be absolutely sure no problems arise, use REMOVE_UNUSED_CONSTANT only at the end of a source file. That insures the .sect directive (which changes the current section name) will not interfere with any section name emitted by the compiler.

An asm() statements accepts one argument: a quoted string.

This particular asm() statement results in two lines of assembly:

 .sect ".const:variable"
 .clink

The space at the beginning of each line is important. Otherwise, the assembler interprets them as labels.

Form the First asm() Line[edit]

Here is the first half of the asm part of the macro again, followed by an explanation that moves from left to right.

<syntaxhighlight lang="c">

  asm(" .sect \".const:" #var "\"\n"           \

</syntaxhighlight>

The beginning is pretty obvious. The \" means actually put a quote inside the string, and do not end the argument to asm(). The :" ends the .const part of the subsection name, followed by the variable part of the subsection name. Those are smooshed together just as in the pragma. The "\"\n" says to smoosh on two more characters: a " and a newline.

Form the Second asm() Line[edit]

Here is the second half of the asm part of the macro, followed by more explanation.

<syntaxhighlight lang="c">

   " .clink")

</syntaxhighlight>

Finally, something normal! It is just another quoted string, the .clink directive explained earlier. Due to the line continuation "\" on the previous line, the compiler acts as if this line were written on the previous line, which means this string is smooshed on to the end of the previous one. Remember the previous string ends with a newline. So, in the compiler output, this forms two lines. As promised, a multiple line asm() statement! Note there is no concluding semi-colon. The user of the macro supplies that semi-colon.

E2e.jpg {{
  1. switchcategory:MultiCore=
  • For technical support on MultiCore devices, please post your questions in the C6000 MultiCore Forum
  • For questions related to the BIOS MultiCore SDK (MCSDK), please use the BIOS Forum

Please post only comments related to the article Automatically Remove Unused Constant Variables here.

Keystone=
  • For technical support on MultiCore devices, please post your questions in the C6000 MultiCore Forum
  • For questions related to the BIOS MultiCore SDK (MCSDK), please use the BIOS Forum

Please post only comments related to the article Automatically Remove Unused Constant Variables here.

C2000=For technical support on the C2000 please post your questions on The C2000 Forum. Please post only comments about the article Automatically Remove Unused Constant Variables here. DaVinci=For technical support on DaVincoplease post your questions on The DaVinci Forum. Please post only comments about the article Automatically Remove Unused Constant Variables here. MSP430=For technical support on MSP430 please post your questions on The MSP430 Forum. Please post only comments about the article Automatically Remove Unused Constant Variables here. OMAP35x=For technical support on OMAP please post your questions on The OMAP Forum. Please post only comments about the article Automatically Remove Unused Constant Variables here. OMAPL1=For technical support on OMAP please post your questions on The OMAP Forum. Please post only comments about the article Automatically Remove Unused Constant Variables here. MAVRK=For technical support on MAVRK please post your questions on The MAVRK Toolbox Forum. Please post only comments about the article Automatically Remove Unused Constant Variables here. For technical support please post your questions at http://e2e.ti.com. Please post only comments about the article Automatically Remove Unused Constant Variables here.

}}

Hyperlink blue.png Links

Amplifiers & Linear
Audio
Broadband RF/IF & Digital Radio
Clocks & Timers
Data Converters

DLP & MEMS
High-Reliability
Interface
Logic
Power Management

Processors

Switches & Multiplexers
Temperature Sensors & Control ICs
Wireless Connectivity