Document macro without expansion - macros

In my C project which I'm documenting using doxygen 1.9.1, I've got several documented macros such as
/**
* #brief Does a thing.
*/
#define DO_THING() someFunc(1, 2, 3)
When I generate the documentation, DO_THING is listed but it shows the expansion (i.e., someFunc(1, 2, 3)). Is there any way to have doxygen hide the expansion? I'd like my macros to be opaque to my users. That is, I'd like them to only know, "There's a macro called DO_THING() and it does a thing."

Doxygen has the possibility to set the maximum number of initializer lines by means of the setting: MAX_INITIALIZER_LINES
MAX_INITIALIZER_LINES
The MAX_INITIALIZER_LINES tag determines the maximum number of lines that the initial value of a variable or macro / define can have for it to appear in the documentation. If the initializer consists of more lines than specified here it will be hidden. Use a value of 0 to hide initializers completely. The appearance of the value of individual variables and macros / defines can be controlled using \showinitializer or \hideinitializer command in the documentation regardless of this setting.
and has the command \hideinitializer
\hideinitializer
By default the value of a define and the initializer of a variable are displayed unless they are longer than 30 lines. By putting this command in a comment block of a define or variable, the initializer is always hidden. The maximum number of initialization lines can be changed by means of the configuration parameter MAX_INITIALIZER_LINES, the default value is 30.
So you can solve your problem by either setting
MAX_INITIALIZER_LINES to `0 though this is valid for all initialized values
for the relevant parts the \hideinitializer

Related

what is the difference between 'define as' to 'define as computed' in specman?

The difference between the two is not so clear from the Cadence documentation.
Could someone please elaborate on the difference between the two?
A define as macro is just a plain old macro that you probably know from other programming languages. It just means that at some select locations in the macro code you can substitute your own code.
A define as computed macro allows you to construct your output code programmatically, by using control flow statements (if, for, etc.). It acts kind of like a function that returns a string, with the return value being the code that will be inserted in its place by the pre-processor.
With both define as and define as computed macros you define a new syntactic construct of a given syntactic category (for example, <statement> or <action>), and you implement the replacement code that replaces a construct matching the macro match expression (or pattern).
In both cases the macro match expression can have syntactic arguments that are used inside the replacement code and are substituted with the actual code strings used in the matched code.
The difference is that with a define as macro the replacement code is just written in the macro body.
With a define as computed macro you write a procedural code that computes the desired replacement code text and returns it as a string. It's effectively a method that returns string, you can even use the result keyword to assign the resulting string, just like in any e method.
A define as computed macro is useful when the replacement code is not fixed, and can be different depending on the exact macro argument values or even semantic context (for example, in some cases a reflection query can be used to decide on the exact replacement code).
(But it's important to remember that even define as computed macros are executed during compilation and not at run time, so they cannot query actual run time values of fields or variables to decide on the resulting replacement code).
Here are some important differences between the two macro kinds.
A define as macro is more readable and usually easier to write. You just write down the code that you want to be created.
Define as computed macros are stronger. Everything that can be implemented with define as, can also be implemented with define as computed, but not vice versa. When the replacement code is not fixed, define as is not sufficient.
A define as macro can be used immediately after its definition. If the construct it introduces is used in the statement just following the macro, it will already be matched. A define as computed macro can only be used in the next file, and is not usable in the same file in which the macro is defined.

Systemverilog: scope of text substitution macro

I read that text substitution macros have global scope in 'verilog'. How does SystemVerilog work? I want to use 2 different definitions of the same text macro in 2 different SystemVerilog files - is that OK to do?
In SystemVerilog, macro definitions are limited to the compilation-unit scope but what that is depends on the tool configuration. From the specification:
The exact mechanism for defining which files constitute a compilation
unit is tool-specific. However, compliant tools shall provide use
models that allow both of the following cases:
a) All files on a given compilation command line make a single
compilation unit (in which case the declarations within those files
are accessible following normal visibility rules throughout the
entire set of files).
b) Each file is a separate compilation unit (in which case the
declarations in each compilation-unit scope are accessible only
within its corresponding file).
Therefore if you use multiple-file compilation units (-mfcu for Modelsim), there will be collisions since the macro namespace will have global scope. However the specification explicitly allows redefinitions so you may not get an error(or warning) in this case, unless your tool supports it.
The text macro name space is global within the compilation unit.
Because text macro names are introduced and used with a leading ‘
character, they remain unambiguous with any other name space. The text
macro names are defined in the linear order of appearance in the set
of input files that make up the compilation unit. Subsequent
definitions of the same name override the previous definitions for the
balance of the input files.
Depending on how you are using macros, you may want to consider using parameters instead. Parameters are essentially constants that are more limited in scope than preprocessor directives. They can also be used to selectively instance code using generate constructs.
You can get the SV specification here for free.
If the desired macro have simuliar structure/format, then you can use macro with arguments. See IEEE1800-2012 Section 22.5.1.
`define myMacro(arg1,arg2) \
prefix_``arg1 = arg2``_postfix
If the desired macro definition is exclusively in its respected file and unique, then you can do the following. All other files will not have an `mymacro that can be called. `undef is from Verilog, IEEE1364-1995 Section 16.3.2, and has been in included into SystemVerilog. You can read more about `undef in the latest revision; IEEE1800-2012 Section 22.5.2.
file1.sv:
`define mymacro abcd
/* SystemVerilog code */
`undef mymacro
file2.sv:
`define mymacro wxyz
/* SystemVerilog code */
`undef mymacro

Confusing about the Emacs custom system

There are several similar setting functions:
set & setq
set-default
defcustom
custom-set-value
custom-set-variables
customize-set-value
customize-set-variable
so, what's the difference between these functions?
If I want setting my own preferences to an add-on, for these scenario:
If a variable setting by defcustom, which setting-function will be better?
And what about a variable setting by defvar?
The short answer to you question is:
use setq or setq-default for variables defined by defvar.
use setq, setq-default, or the Customize mechanism for variables defined by defcustom
Below is the long answer.
The functions that you are going to use are the following:
set is the main function to set the value of a variable.
setq is another version that automatically quotes its first argument. This is useful since quoting the first argument is what you want to do almost all the time.
Some variables cannot be set globally. Whenever you set the variable it is only set for the current buffer. If you want to simulate setting this variable globally you use set-default or setq-default.
The functions that a package writer uses are:
defvar which allows the package writer to define a variable and to give some documentation. This function is not required but makes the life of users easier.
defcustom builds on defvar. It tells emacs that it is a variable, and it allows the developer to create a custom interface to set the value. The developer can say, things like "this variable can contain only the value 'foo or 'bar".
Setting variables can be done two ways:
if defvar was used, the values can only be set by the user in its .emacs by using the set function (or variants)
if defcustom was used, the values can be set using set (see 1.) OR by using Customize. When using the customize mechanism, emacs will generate some code that it will place in custom-set-variables. The user should not use this function.
They are, largely all paths to the same thing. There are some important differences though. The best way to get to know them is to read the manuals for Emacs and Elisp (see C-h i). Off the top of the head though:
set is a "low-level" variable assignment
(setq foo bar) is shorthand for (set (quote foo) bar)
(set-default foo bar) means "unless there is a more explicitly scoped definition of foo in the current buffer, use the value bar", and applies to all buffers.
defcustom is used to mark a variable as one that the user is expected to be able to safely modify through the customize feature.
custom-set-value and customize-set-value are two names that point to the same function. They're convenience methods for working with the customize system.
custom-set-variables and customize-set-variables are used to make some set of customized-through-customize variables active, IIRC.
In general, it's recommended to use M-x customize to change things around. You're free to set things defined with defcustom using set or setq in your .emacs, the customize system will warn you about it if you later change it via customize though.
defcustom is generally only used by people writing packages meant for distribution, and I don't think I've seen anyone use custom-set-* outside of files internal to customize. setq is very common in people's initialization files for setting things up how they like them, regardless of whether those things are marked for use with customize or not.
I don't have a full understanding of all this, hopefully someone else can shed more light, but I think that that's a fairly good overview :P
set and setq are the lowest level primitives used for assigning any kind of variable.
set-default and setq-default are emacs extensions that go along with buffer-local variables, to allow setting the default values used for new buffers.
3-7. All the "custom" stuff is a later addition that was designed to support a user interface for managing variables that are intended to be used as user preferences.
defcustom is similar to defvar, but allows you to specify a place in the hierarchy of options, as well as data type information so that the UI can display the value as a menu, or automatically convert user input to the appropriate type.
I don't think there is a custom-set-value function.
custom-set-variables is used by the customize UI when saving all the user's options. It lists all the variables that the user has changed from their defaults.
6-7. custom-set-value and custom-set-variable are used by the Customize UI to prompt the user for the current and default values of an option variable, and assign them. You don't normally call this yourself.
Just as addition, the differences between those commands have increased due to the introduction of lexical binding, though those differences will not really be relevant if you just want to customize some variables.
The def... constructs declare global variables. The set... functions set variables, whether global or local. When x is neither a local variable (a formal parameter of the current function or declared by a let form or similiar) nor defined by a def... form and you write (setq x 0) the byte compiler will even show a warning
Warning: assignment to free variable `x'
Variables declared with defvar, defcustom, defconst are dynamically bound, i.e. when you have a construct
(let ((lisp-indent-offset 2))
(pp (some-function)))
the function some-function will see the change of the global variable lisp-indent-offset.
When a variable is not dynamically bound, in something like
(let ((my-local-var 1))
(some-function))
where my-local-var has no global value, then some-function will not see the assigned value, as it is lexically scoped.
On the other hand, dynamically scoped variables will not be captured into lexical closures.
More details can be seen in http://www.gnu.org/software/emacs/manual/html_node/elisp/Lexical-Binding.html

How do I search for variable names in the editor?

In functions, the MATLAB editor displays a warning when a defined variable is not subsequently used before the function ends or before the variable is overwritten. This obviously tells me that the editor has a way of searching for occurrences of given variables in the code.
Can I do this manually? The Find function is obviously limited here, since it only searches the body of text in the editor window (including comments) for matches of the search string. This makes it very inconvenient when searching for variables with short names (such as the by me commonly used "a").
I cannot tell you about previous versions of the built-in editor, but at least from 2011b, the righthand side margin of the editor creates color tags for:
Warnings, tagged in orange
Errors, tagged in red color
Variable/function occurrence: tagged in dark gray, for selected text.
The third of them is what you are looking for. You just have to double click on a variable name or a function name to select it and your Matlab editor will automatically highlight the rest of the occurrences of the very same identifier, tagging them on the righthand side ribbon with the grey mark I mentioned above.
You can limit the search to match case and whole word, which will give you only this variable, either in comment or not.
BTW, you shouldn't use variable names like a,b,c. It makes the code harder to read and to maintain. Even if you have dummy variables like in loops and temporary ones, use for example indexFiles, or tempValue
You can also use some regular expression to match the variable names in your code.
If you'll assume that any variable name is separated from the rest of the code by any of linefeed tab space ! " # $ % & ' ( ) * + , - . / : ; < = > ? [ \ ] ^ `` { | } ~, then you can create a small function that takes the function name as input and outputs the lines in which the variable name is mentioned. However, this approach doesn't separate function names and variable names, but you should have some standard for separating them anyway. I use this approach to change variable names of my MATLAB code (but my code for that is written in awk, not in MATLAB).
And I wonder what you'll do when you have a complex program with thousands or tens of thousands of lines of code and your variables are named a, b, c and so on...

Doxygen conditional compilation does not produce documentation

I'm a relative beginner with doxygen, and am documenting a C program
Part of the code is:
\#include "options.h"
// options.h contains
\#define VAL0 0 // Possible values for PARAM
\#define VAL1 1
\#define PARAM VAL0
// Here's the conditional compilation
\#if (PARAM == VAL0)
// code chunk, which doesn't get compiled by Doxygen
\#endif
The code compiles with GCC as expected, but I get no Doxygen documentation
OK, Doxygen doesn't expand macros, so I tried:
\#define SYMEQ(A, B) (A == B) ? 1 : 0
\#if SYMEQ(PARAM, VAL0)
// code chunk
\#endif
Set the Doxygen:
MACRO_EXPANSION = YES
EXPAND_ONLY_PREDEF = YES
No Predefined macros
EXPAND_AS_DEFINED = SYMEQ
No doxygen output from the conditional part, just up to it
I also tried EXPAND_AS_DEFINED SYMEQ(A, B)
Also no luck
I found a few examples with simple names, then #ifdef NAME \code #endif, but none with macro functions
I just had the problem #ifdef CONDITION \code not compiled by doxygen\ #endif and fixed it by brute force, i.e, appending the conditions to the setting PREDEFINED=CONDITION1 CONDITION2 ... manually.
I tried the header file solution -- generate a file with conditions and include it by setting SEARCH_INCLUDES, INCLUDE_PATH and INCLUDE_FILE_PATTERNS -- but it did not work. From the doxygen manual, I think it requires to explicitly #include "the condition file" in the source files, which means to modify the source code, so I give up.
SEARCH_INCLUDES:
If the SEARCH_INCLUDES tag is set to YES (the default) the includes files in the INCLUDE_PATH (see below) will be searched if a #include is found.
MACRO_EXPANSION and EXPAND_ONLY_PREDEF only control whether a macro will be expanded in your code, not how it will be evaluated in conditional preprocessor blocks. For example, if you had code like:
#define RET_TYPE int
/**
* Some function
*/
RET_TYPE func(void);
With MACRO_EXPANSION=NO, this will be documented by doxygen as RET_TYPE func(void), the macro isn't expanded. With MACRO_EXPANSION=YES, this will be documented as int func(void), the macro is expanded and the resulting signature is documented.
To control conditional code, you'll want to focus on the ENABLE_PREPROCESSING. If this option is set to NO, conditional code will be ignored, and all code within the condition will be documented. If it is set to YES, the conditional code will be evaluated, and only blocks for which the condition matches will be documented. In this case, you'll need to make sure that all of the values being evaluated are defined correctly, this can be accomplished by allowing doxygen to evaluate include files (see SEARCH_INCLUDES, INCLUDE_PATH and INCLUDE_FILE_PATTERNS options), or by predefining the macros to have a particular value (see PREDEFINED).