sscanf behavoir

J

Joachim Schmitz

Hi folks

What would be the expected and correct output of the following

#include <stdio.h>

int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);

sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);

return 0;
}

On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12

on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.

Which is correct?
Bye, Jojo
 
M

mark_bluemel

Hi folks

What would be the expected and correct output of the following

#include <stdio.h>

int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);

sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);

return 0;

}

On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12

on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.

Which is correct?

sscanf returns an integer which is the count of values assigned. Your
program would be improved by showing this information, in my opinion.

On my gcc/glibc system I get your second result and in both cases 3
values are reported as assigned. The same result is obtained on AIX,
using the IBM xlc compiler and IBM's C library implementation. This is
the result I'd expect.
 
J

Joachim Schmitz

Hi folks

What would be the expected and correct output of the following

#include <stdio.h>

int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);

sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);

return 0;

}

On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12

on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.

Which is correct?

sscanf returns an integer which is the count of values assigned. Your
program would be improved by showing this information, in my opinion.

On my gcc/glibc system I get your second result and in both cases 3
values are reported as assigned. The same result is obtained on AIX,
using the IBM xlc compiler and IBM's C library implementation. This is
the result I'd expect.
I did try that too and sscanf returns 3 on all cases. What I'm concerned
about thoug is the %n conversion that does not seem to work properly. So
sscanf did process at least 9 of it's input characters "(10,20,30" as the
corresponding variables are filled, but regardless %n doesn't show that.
From the sscanf man-page:

n Consumes no input. The corresponding pointer
parameter is a pointer to an integer into
which is written the number of characters
read from the input string so far by this
function. The assignment count returned at
the completion of this function is not
incremented.


Bye, Jojo
 
G

Gunvant Patil

Hi folks

What would be the expected and correct output of the following

#include <stdio.h>

int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);

sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);

return 0;

}

On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12

on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.

Which is correct?
Bye, Jojo

I think second result is expected cause %n should yield the number of
characters consumed THUS far from the input and in second case input
consumption will end at ")" only and %n is coming later to that hence
it's undefined.
The C standard says: Execution of a %n directive does not increment
the assignment count returned at the completion of execution but the
Corrigendum seems to contradict this. Probably it is wise not to make
any assumptions on the effect of %n conversions on the return value.

-Cheers,
Gunvant
~~~~~~~~
No trees were killed in the sending of this message. However a large
number of electrons were terribly inconvenienced.
 
J

Joachim Schmitz

Gunvant Patil said:
Hi folks

What would be the expected and correct output of the following

#include <stdio.h>

int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);

sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);

return 0;

}

On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12

on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.

Which is correct?
Bye, Jojo

I think second result is expected cause %n should yield the number of
characters consumed THUS far from the input and in second case input
consumption will end at ")" only and %n is coming later to that hence
it's undefined.
I don't understand you here, in both cases the input ends at the ")" and %n
is immediatelly after that.
The C standard says: Execution of a %n directive does not increment
the assignment count returned at the completion of execution but the
Corrigendum seems to contradict this. Probably it is wise not to make
any assumptions on the effect of %n conversions on the return value.
Í've seen these 4 line in the Linux man-page, but only there. What does the
standard actually say? Chapter and verse?

Bye, Jojo
 
M

mark_bluemel

Gunvant Patil said:
Hi folks
What would be the expected and correct output of the following
#include <stdio.h>
int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);
sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);
return 0;
}
On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12
on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.
Which is correct?
Bye, Jojo
I think second result is expected cause %n should yield the number of
characters consumed THUS far from the input and in second case input
consumption will end at ")" only and %n is coming later to that hence
it's undefined.

I don't understand you here, in both cases the input ends at the ")" and %n
is immediatelly after that.

That's not actually the case.

In the second case "(10,20,30 )", the scanning fails at the space
character.

If sscanf gives up at that point (it found a character which was
neither part of an integer nor a right parenthesis), it may well not
even consider the "%n".
 
E

Eric Sosman

Joachim said:
Hi folks

What would be the expected and correct output of the following

#include <stdio.h>

int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);

sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);

return 0;

}

On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12

on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.

Which is correct?
sscanf returns an integer which is the count of values assigned. Your
program would be improved by showing this information, in my opinion.

On my gcc/glibc system I get your second result and in both cases 3
values are reported as assigned. The same result is obtained on AIX,
using the IBM xlc compiler and IBM's C library implementation. This is
the result I'd expect.
I did try that too and sscanf returns 3 on all cases. What I'm concerned
about thoug is the %n conversion that does not seem to work properly. So
sscanf did process at least 9 of it's input characters "(10,20,30" as the
corresponding variables are filled, but regardless %n doesn't show that.
[...]

Because the %n is never processed. The ')' in the format
string does not match the space character after the "30", so
conversion stops. Three integers have been converted and
assigned successfully, so sscanf() returns the value 3; the
matching failure on the ')' does not affect what has already
happened.
 
G

Gunvant Patil

Hi folks
What would be the expected and correct output of the following
#include <stdio.h>
int main (void)
{
char buffer1[] = "(10,20,30)";
char buffer2[] = "(10,20,30 )"; /* add two white spaces between 30
and ) */
int var1, var2, var3;
int i = 11111;
int j = 22222;
sscanf (buffer1,"(%d,%d,%d)%n",&var1,&var2,&var3,&i);
printf ("%s -> %d\n",buffer1,i);
sscanf (buffer2,"(%d,%d,%d)%n",&var1,&var2,&var3,&j);
printf ("%s -> %d\n",buffer2,j);
return 0;
}
On one platform I get:
(10,20,30) -> 10
(10,20,30 ) -> 12
on another I get:
(10,20,30) -> 10
(10,20,30 ) -> 22222
i.e. j is left unmodified.
Which is correct?
Bye, Jojo
I think second result is expected cause %n should yield the number of
characters consumed THUS far from the input and in second case input
consumption will end at ")" only and %n is coming later to that hence
it's undefined.

I don't understand you here, in both cases the input ends at the ")" and %n
is immediatelly after that.

In second case input scanning will fail at white space and not at ')'
Í've seen these 4 line in the Linux man-page, but only there. What does the
standard actually say? Chapter and verse?

Yes indeed those lines are from linux man pages and here are some
references from C99

7.24.2.2#12

7.24.2.2#16

7.19.6.2 #10
Bye, Jojo- Hide quoted text -

- Show quoted text -

-Cheers,
Gunvant
~~~~~~~~
No trees were killed in the sending of this message. However a large
number of electrons were terribly inconvenienced.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,581
Members
45,056
Latest member
GlycogenSupporthealth

Latest Threads

Top