local variables converted into global variables? - c

I am passed in a C file. The C file contains functions which contain local variables. Given any C file, i have to be able to find the local variables within a specific method (which the user specifies) and make them global. (specifications for another application which can only handle global variables)...
What is the easiest way to do this? Would it be through shell scripting or should it directly in C. Should i use regex? Am i thinking about doing this the wrong way?
Any help would be appreciated

You are looking for a specific context of variables, in your case the context is local variables declared inside of a function. A regular expression can be used to pull out a function definition, but some kind of token parser would be much better.
Using a simplified grammar for C it can be found that you can get the function strings themselves and from there you can find the local variables themselves.
But, if the C code passed in is in a specific format, IE local variables are at the top of the function definition then a simple regular expression can be used.

C99 will allow variables to be declared throughout the function, within blocks etc., so the task of identifying them is complicated. It might be possible to leverage a lexer/parser like yacc and flex to tokenise a C source file, then pull the variable declarations out of the generated structures. Making this general purpose is likely to be a lot of work.

Related

Equivalent of static local variables inside Scilab function

I have been looking for a way how to define persistent local variables inside
the Scilab function. It could be said that I have been looking for a way how
to define equivalent of the static local variables known from the C programming language in the Scilab function. Can anybody help?
There are at least 2 ways to get a similar feature:
using global variables (to get some static):
https://help.scilab.org/docs/6.1.1/en_US/global.html
This is likely the most "standard" way.
You may define them in a local scope (for instance in a
function), but then there is no way to restrict the access to
them to the place where they have been defined.
using variables in a TCL "interpreter":
https://help.scilab.org/docs/6.1.1/en_US/TCL_CreateSlave.html
https://help.scilab.org/docs/6.1.1/en_US/TCL_SetVar.html
https://help.scilab.org/docs/6.1.1/en_US/TCL_GetVar.html
A TCL interpreter is a kind of "namespace". It is also a global object.
You may defined as many interpreters as you want.
But not all types of data can be recorded as a TCL variable.
And all data are (recorded and) retrieved as strings (and only in single precision for decimal numbers. May be it's possible to go beyond by using some TCL options).
In the opposite, there is no data type limitations for global variables, that are recorded as is, without any conversion into strings.
But there is no way to define "global namespaces" (may be as fields of a global structure..)

What sense does it make to declare a function more than one time in C?

I've seen a couple of times that the prototype declaration of a function in the header was literally repeated in the c-file.
It is possible to declare a function more than one time in C - but what sense does it make? Is it just for better readability or is there some deeper insight which I am missing?
It is possible. It doesn't make any sense.
But it does not cause any harm either. You can declare a function as many times as you like, but each such declaration must be identical to the others. So it is pointless to do so. As someone suggested, maybe it is a copy/paste error.
You can only have one function definition though, which should always be in the c file.
This is how you should do it:
Function declarations which is part of the caller's interface should be in the h file, and there only.
Function declarations of local (private) functions that are only available from inside the c file itself, should be in the c file, and there only. Such functions should be declared and defined as static.
Duplicate function declarations serve no useful semantic purpose, but they may arise for historical reasons, because of local coding conventions, or for some other reason.
For example, it may be a local coding convention that every function in each source file is prototyped at the beginning of that file. That has some minor practical utility, such as serving as a manifest of the functions defined in each file, and making the functions inside each file able to ignore any concern about whether other functions in the same file are declared in a header.
Additionally, multiple declarations of the same function or object don't necessarily have to be identical, they only need to be compatible. Under some circumstances it may makes sense to provide a less specific prototype in a header and a more specific one in the source file containing the function definition (which itself serves as yet another declaration).

Static variables clarification

There might be another question like this on stack but I am not completely sure. So on to my question. My professor told everyone, "NEVER USE GLOBAL VARIABLES". But she said that static variables are allowed as long as you give a good enough reason. So my question is, under her criteria, is a static variable declared at the global level ok?
Unfortunately static has two meanings in C. When applied to a global variable, it means that the visibility of this symbol is in the file scope. When applied to a local variable, it means that this variable retains its value between calls (i.e., it's not really a local variable). Your professor is referring to the latter, not the former, when she says they are allowed.
There are times when global variables are useful. Consider stderr: it would be a pain to have to define it in every file you needed to use it in; it is sensibly defined as a global variable.
There are times when it is sensible to store a variable at file scope without external linkage (which you do using static as part of the definition of the variable, outside the scope of any function). For example, if you have a suite of functions which need to share some state but the API does not pass a handle back to the calling code (so there isn't an analogue of open and close — or create and destroy), then one or more static variables at file scope make sense.

Can I detect the existence of a local variable inside a macro?

Is there a way to safely check to see whether some named variable (let's call it "foo") is present in the current scope? I'd like to have a macro that, say, makes use of "foo" if it's present, otherwise does something else. Are there any runtime tricks I can make use of here?
(The actual context is trying to solve this problem, but I realized that one could be a special case of this one, so a separate question seemed also interesting.)
Unfortunately, no. The compiler is responsible for parsing variable names and assigning scopes to them, and the preprocessor runs before the compiler. So it has no access to that information.

Is it possible to avoid global variables in a strictly procedural program?

Being a developer born and raised on OO, I was curious to hear how it's possible to avoid global state in a procedural program.
You can also write object-oriented code in C. You don't get all the C++ goodies and it's ugly, and you have to manually pass the this pointer (I've seen self used for this, in order to make it compatible with C++), but it works. So technically, you don't need global state in pure procedural languages for the very same reasons you don't need it in object-oriented languages. You just have to pass the state around explicitly, rather than implicitly like in OO languages.
As an example, look at how the file I/O functions in the C standard library work with pointer to FILE objects that are (largely) opaque. Or look at how OS APIs deal with handles and such to encapsulate information. A program creates objects, uses APIs that act on those objects and closes/deletes the objects - all using straight C.
A global variable is nothing but an implicit procedure argument. Make it explicit and the global variable goes away.
Note: the fact that you no longer use a global variable does not mean that you no longer use global state! What we did above was just a purely syntactical transformation, the semantics of the program haven't changed at all. It's just as non-composable, non-modular, non-threadsafe, non-parallelizable as it was before.
All OO is a mindset and a whole bunch of compiler support.
You can achieve much the same by discipline, coding conventions, and passing around structures in most languages.
For example I used to have functions/procedures prefixed with their module identity, taking the first parameter as being the related module struct.
// System.h
typedef struct _System
{
struct _System *owner;
LinkedList *elements;
} System;
// System.c
int System_FindName ( System * system, char *name)
{
..
}
etc..
I'd really seriously not like to have to go back to coding like this though. I'm very happy that I haven't had to write and debug a linked list for at least 18 years. It was hard back then without the internet and sitting there isolated in the corner of a cold brightly lit room with green phosphors burning into your retina...
Of course. Just declare a struct somewhere, allocate some memory for it, pass the pointer to the allocated memory to an initialization function, and off you go. Just pass the pointer to all the functions that require using the struct.
Though the question arises as to where you store the pointer to the data you don't want to be global, and then you may end up with a global pointer ;-)
You can have variables on stack or in heap that will exist during all the program life.
Passing object style structure pointers to every function is a good way to have OO C coding style.
(I would suggest to have a look in linux sources)
You could try, as an example, create with dia (the diagramming tool), a simple class (for example, a square).
http://projects.gnome.org/dia/
http://dia-installer.de/index_en.html
Then, you can transform that class in C code using dia2code:
http://dia2code.sourceforge.net/
Specifically, say you created the class square inside the square.dia diagram. Then, you type:
$ dia2code -t c square.dia
... and you will see that it is possible to convert any object-oriented programming in a C program without global variables. Explore the created files square.c and square.h
NOTE: in Windows, you'll need a workaround in order to make dia2code work. Before using dia2code, change square.dia to square.zip, unzip it, and rename the result as square.dia
Simple. Whenever a procedure accesses a global variable, then give this variable as an argument to the procedure instead, either by value or by reference or by pointer, or by whatever your programming language provides. After that there is no more need for the variable to be global.

Resources