By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
446,188 Members | 977 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 446,188 IT Pros & Developers. It's quick & easy.

variable number of arguments

P: n/a
I read the C FAQ question on passing a variable number of arguments,
but it didn't help. The example assumes all arguments are of the same
type.

I want to create a function "trace" that can be used like this:

trace( "Err", errtType, lineNum, NULL) /* where errType is char* and
lineNum is
an int */

trace("Err", lineNum, NULL);

trace( lineNum, "Err", funcName, NULL) /* where funName is char * */

The problem is that I don't know the order and the variable types of
the arguments passed.

How can I implement trace?
Nov 14 '05 #1
Share this Question
Share on Google+
10 Replies


P: n/a
th***********@hotmail.com (The Directive) writes:
I want to create a function "trace" that can be used like this:

trace( "Err", errtType, lineNum, NULL) /* where errType is char* and
lineNum is
an int */

trace("Err", lineNum, NULL);

trace( lineNum, "Err", funcName, NULL) /* where funName is char * */

The problem is that I don't know the order and the variable types of
the arguments passed.

How can I implement trace?


You can't. trace() has to know the types of the arguments, or be
able to figure them out.
--
int main(void){char p[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuv wxyz.\
\n",*q="kl BIcNBFr.NKEzjwCIxNJC";int i=sizeof p/2;char *strchr();int putchar(\
);while(*q){i+=strchr(p,*q++)-p;if(i>=(int)sizeof p)i-=sizeof p-1;putchar(p[i]\
);}return 0;}
Nov 14 '05 #2

P: n/a
Hi
I already wrote a function of the same type. But I believe that it is
necessary to have at least a parameter which will describe the following.
Like does it printf, you could have: trace(char format,...);
with for example:
trace("Err Line:%d Type:%c File name:%s,__LINE__,mytype,__FILE__);
If you want, I can send my source
Dominique

"The Directive" <th***********@hotmail.com> a écrit dans le message de
news:84**************************@posting.google.c om...
I read the C FAQ question on passing a variable number of arguments,
but it didn't help. The example assumes all arguments are of the same
type.

I want to create a function "trace" that can be used like this:

trace( "Err", errtType, lineNum, NULL) /* where errType is char* and
lineNum is
an int */

trace("Err", lineNum, NULL);

trace( lineNum, "Err", funcName, NULL) /* where funName is char * */

The problem is that I don't know the order and the variable types of
the arguments passed.

How can I implement trace?

Nov 14 '05 #3

P: n/a
Oups error:
trace(char *format, ...);

"DomiPi" <ak******@tiscali.be> a écrit dans le message de
news:bt**********@news.worldonline.be...
Hi
I already wrote a function of the same type. But I believe that it is
necessary to have at least a parameter which will describe the following.
Like does it printf, you could have: trace(char format,...);
with for example:
trace("Err Line:%d Type:%c File name:%s,__LINE__,mytype,__FILE__);
If you want, I can send my source
Dominique

"The Directive" <th***********@hotmail.com> a écrit dans le message de
news:84**************************@posting.google.c om...
I read the C FAQ question on passing a variable number of arguments,
but it didn't help. The example assumes all arguments are of the same
type.

I want to create a function "trace" that can be used like this:

trace( "Err", errtType, lineNum, NULL) /* where errType is char* and
lineNum is
an int */

trace("Err", lineNum, NULL);

trace( lineNum, "Err", funcName, NULL) /* where funName is char * */

The problem is that I don't know the order and the variable types of
the arguments passed.

How can I implement trace?


Nov 14 '05 #4

P: n/a
"DomiPi" <ak******@tiscali.be> wrote in message
news:bt**********@news.worldonline.be...
Oups error:
trace(char *format, ...);


Oups (sic) error: top-post.

<rest snipped for clarity>

Peter
Nov 14 '05 #5

P: n/a
Peter Pichler wrote:
"DomiPi" <ak******@tiscali.be> wrote in message
Oups error:
trace(char *format, ...);


Oups (sic) error: top-post.

<rest snipped for clarity>


A fine riposte.

--
Chuck F (cb********@yahoo.com) (cb********@worldnet.att.net)
Available for consulting/temporary embedded and systems.
<http://cbfalconer.home.att.net> USE worldnet address!
Nov 14 '05 #6

P: n/a
"DomiPi" <ak******@tiscali.be> writes:
I already wrote a function of the same type. But I believe that it is
necessary to have at least a parameter which will describe the following.
Like does it printf, you could have: trace(char format,...);
with for example:
trace("Err Line:%d Type:%c File name:%s,__LINE__,mytype,__FILE__);
If you want, I can send my source


There are a number of ways that a function taking a variable number of
arguments can be told the number and type of the arguments. printf's
format string is probably the most common. If all the arguments
(after the initial one(s)) are of the same type, a sentinel value,
such as a null pointer, can be used to mark the end of the list.

Another approach (one that I've never actually seen) is for every
other argument to specify the type of the following one:

foo('i', 42,
'd', 123.4,
's', "hello");

Whatever method is used, it's the caller's responsibility to make sure
everything is consistent. If you pass a pointer where the function
looks for an int, you're not likely to get any help from the compiler.

--
Keith Thompson (The_Other_Keith) ks***@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://www.sdsc.edu/~kst>
Schroedinger does Shakespeare: "To be *and* not to be"
Nov 14 '05 #7

P: n/a
From everyone's responses, I conclude that there's no easy, clean way
to pass a variable number of arguments with variable unknown types in
C. Correct? That information must be passed as another argument. What
was the reasoning for the C language designers to implement it this
way? Is it a weakness of the language?

--The Directive

Keith Thompson <ks***@mib.org> wrote in message news:<ln************@nuthaus.mib.org>...
"DomiPi" <ak******@tiscali.be> writes:
I already wrote a function of the same type. But I believe that it is
necessary to have at least a parameter which will describe the following.
Like does it printf, you could have: trace(char format,...);
with for example:
trace("Err Line:%d Type:%c File name:%s,__LINE__,mytype,__FILE__);
If you want, I can send my source


There are a number of ways that a function taking a variable number of
arguments can be told the number and type of the arguments. printf's
format string is probably the most common. If all the arguments
(after the initial one(s)) are of the same type, a sentinel value,
such as a null pointer, can be used to mark the end of the list.

Another approach (one that I've never actually seen) is for every
other argument to specify the type of the following one:

foo('i', 42,
'd', 123.4,
's', "hello");

Whatever method is used, it's the caller's responsibility to make sure
everything is consistent. If you pass a pointer where the function
looks for an int, you're not likely to get any help from the compiler.

Nov 14 '05 #8

P: n/a

On Mon, 11 Jan 2004, The Directive wrote:

From everyone's responses, I conclude that there's no easy, clean way
to pass a variable number of arguments with variable unknown types in
C. Correct? That information must be passed as another argument. What
was the reasoning for the C language designers to implement it this
way? Is it a weakness of the language?


Please snip the part of the previous message to which you're not
responding. And don't top-post. http://www.google.com/search?q=top+post

Now, as to your question: Correct. That information (about types)
must be passed as another argument, or built into the structure of the
arguments in the first place. (For example, you could pass a list of
positive integers to a function, and end the list with -1. The
function would know to stop reading arguments when it hit that -1.)
The C language was designed this way because it's incredibly easy
to code, and it's pretty fast [with relatively naive optimization], too,
compared to other ways. Compare the C model to the "Pascal" model,
which can't support variadic functions at all. Search Google for
"argument passing conventions," and then try comp.compilers,
comp.programming, or a similar group if you have implementation
questions.
It's a weakness of the language when compared to languages that
provide more functionality (such as a count of arguments magically
supplied by the compiler); but off the top of my head, the only
language I know that does better is Matlab, and it's got its own
weaknesses. :) It's a trade-off between ease of implementation, power,
and user-friendliness. Since most users don't define functions where
they don't know what they're going to be passing as arguments, it
probably didn't seem a big deal when C was being standardized.

Historical note: I seem to recall that in pre-1989 days, there
was no [de facto] language support for variadic functions at all.
printf and scanf worked by magic; the user was not generally able to
write his own printf-alikes. Do I recall correctly?

-Arthur

Nov 14 '05 #9

P: n/a
"Arthur J. O'Dwyer" <aj*@nospam.andrew.cmu.edu> writes:
[...]
Historical note: I seem to recall that in pre-1989 days, there
was no [de facto] language support for variadic functions at all.
printf and scanf worked by magic; the user was not generally able to
write his own printf-alikes. Do I recall correctly?

-Arthur


There was a <varargs.h> header that predated the current <stdarg.h>
header. Since <stdarg.h> is in the 1989 ANSI standard, <varargs.h>
must have existed before 1989.

But I think that there was a time, before <varargs.h> was invented,
when printf and scanf worked by magic (e.g., by explicitly computing
stack offsets for successive arguments).

--
Keith Thompson (The_Other_Keith) ks***@mib.org <http://www.ghoti.net/~kst>
San Diego Supercomputer Center <*> <http://www.sdsc.edu/~kst>
Schroedinger does Shakespeare: "To be *and* not to be"
Nov 14 '05 #10

P: n/a
Keith Thompson <ks***@mib.org> writes:
There was a <varargs.h> header that predated the current <stdarg.h>
header. Since <stdarg.h> is in the 1989 ANSI standard, <varargs.h>
must have existed before 1989.

But I think that there was a time, before <varargs.h> was invented,
when printf and scanf worked by magic (e.g., by explicitly computing
stack offsets for successive arguments).


Here's the printf() from the Lions Book circa 1976. All typos
are mine.

/*
* Scaled down version of C Library printf.
* Only %s %l %d (==%l) %o are recognized.
* Used to print diagnostic information
* directly on console tty.
* Since it is not interrupt driven,
* all system activities are pretty much
* suspended.
* Printf should not be used for chit-chat.
*/
printf(fmt,x1,x2,x3,x4,x5,x6,x7,x8,x9,xa,xb,xc)
char fmt[];
{
register char *s;
register *adx, c;

adx = &x1;
loop:
while((c = *fmt++) != '%') {
if(c == '\0')
return;
putchar(c);
}
c = *fmt++;
if(c == 'd' || c == 'l' || c == 'o')
printn(*adx, c=='o'? 8: 10);
if(c == 's') {
s = *adx;
while(c == *s++)
puthcar(c);
}
adx++;
goto loop;
}
--
int main(void){char p[]="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuv wxyz.\
\n",*q="kl BIcNBFr.NKEzjwCIxNJC";int i=sizeof p/2;char *strchr();int putchar(\
);while(*q){i+=strchr(p,*q++)-p;if(i>=(int)sizeof p)i-=sizeof p-1;putchar(p[i]\
);}return 0;}
Nov 14 '05 #11

This discussion thread is closed

Replies have been disabled for this discussion.