From: Andrew Falanga on
Hi,

Couple of disclaimers. I'm using VS2008 so the compiler errors come
from that. Though I'm using the sockaddr_in structure in my code, and
for this example, this question is not about socket programming.

I have the following:

sockaddr_in foo; // sockaddr_in is a struct for those not familiar
foo.sin_port = 5075;

int main() {
// do some important stuff
return 0;
}

In this form, I get the following errors:
error C2143: syntax error : missing ';' before '.'
error C4430: missing type specifier - int assumed.
error C2371: 'foo' : redefinition; different basic types

What's interesting is that *BEFORE* I place that assignment of 5075 to
foo.sin_port and I hover over the object named foo, IntelliSense sees
it as an object of type sockaddr_in. However, after I make that
assignment, IntelliSense says that foo is an object of type int. If
the assignment is moved to inside the body of main( ), there's no
problem. The compiler is happy.

I know I'm violating some language constraint but I can't remember
what and the FAQ for this group didn't have a question regarding
structs, nor did the C++ FAQ-Lite mention this. Also, a very brief
few minutes searching through the current draft for the C++ standard
didn't mention this, or more precisely, I didn't enter the correct
search phrases. Would someone here, more knowledgeable than I,
straighten me out?

Thanks a lot,
Andy
From: Richard Heathfield on
Andrew Falanga wrote:
> Hi,
>
> Couple of disclaimers. I'm using VS2008 so the compiler errors come
> from that. Though I'm using the sockaddr_in structure in my code, and
> for this example, this question is not about socket programming.
>
> I have the following:
>
> sockaddr_in foo; // sockaddr_in is a struct for those not familiar

Just out of curiosity, what happens if you change it to:

struct sockaddr_in foo;

?

--
Richard Heathfield <http://www.cpax.org.uk>
Email: -http://www. +rjh@
"Usenet is a strange place" - dmr 29 July 1999
Sig line vacant - apply within
From: Keith Thompson on
Andrew Falanga <af300wsm(a)gmail.com> writes:
> Couple of disclaimers. I'm using VS2008 so the compiler errors come
> from that. Though I'm using the sockaddr_in structure in my code, and
> for this example, this question is not about socket programming.
>
> I have the following:
>
> sockaddr_in foo; // sockaddr_in is a struct for those not familiar

And where is it declared? I presume it's declared in some header that
you've #included, but you didn't show us the #include directive. In
short, you haven't shown us your actual code, only an approximation of
it. In some cases, that can make it impossible to diagnose the
problem. (In this case, you're lucky; the problem happens to be
a fairly obvious one.)

Is sockaddr_in a struct ("struct sockaddr_in { ... }") or a typedef?
If you're compiling C and it's not a typedef, then you have to refer
to it as "struct sockaddr_in". If you're compiling C++ *or* it's
a typedef, you can refer to it just as "sockaddr_in", as you've done
here. Since you didn't get an error message on the declaration of
foo, you're probably ok.

> foo.sin_port = 5075;

Here's the problem. This is an assignment statement. Statements are
only allowed in function bodies. Outside function bodies, you can
only have declarations.

So why didn't the compiler just tell you something like "statement
not allowed in this context"? Probably because it's a syntax
violation, not a constraint violation. The compiler isn't looking
for a statement there, so it doesn't recognize it as a statement;
it's just an invalid token sequence. The '.' token can't legally
appear where you put it. When the compiler sees it, it tries
to recover by making a guess about what you might have meant.
Its best guess is that you meant to write "foo;", which it would have
recognized as a declaration with a missing type specifier (which
it then complains about). It probably discarded the ".sin_port =
5075"; that's a fairly common recovery strategy.

In C90, but not in C99 or C++, a declaration with a missing type
specifier is assumed to declare something of type int. (In pre-ANSI
C, "foo;" would have been a valid declaration, equivalent to "int
foo;".) Apparently the compiler recognizes that obsolete form for
the purpose of diagnosing errors.

> int main() {
> // do some important stuff
> return 0;
> }
>
> In this form, I get the following errors:
> error C2143: syntax error : missing ';' before '.'
> error C4430: missing type specifier - int assumed.
> error C2371: 'foo' : redefinition; different basic types

I presume your compiler reports the line number for each error
message. You probably got all three errors on the same line, the
(intended) assignment statement. It would have been helpful if you
had told us that, either by showing the line numbers or by telling
us that all three errors referred to the assignment statement.

> What's interesting is that *BEFORE* I place that assignment of 5075 to
> foo.sin_port and I hover over the object named foo, IntelliSense sees
> it as an object of type sockaddr_in. However, after I make that
> assignment, IntelliSense says that foo is an object of type int. If
> the assignment is moved to inside the body of main( ), there's no
> problem. The compiler is happy.
>
> I know I'm violating some language constraint but I can't remember
> what and the FAQ for this group didn't have a question regarding
> structs, nor did the C++ FAQ-Lite mention this. Also, a very brief
> few minutes searching through the current draft for the C++ standard
> didn't mention this, or more precisely, I didn't enter the correct
> search phrases. Would someone here, more knowledgeable than I,
> straighten me out?

Keep in mind that this newsgroup deals with both C and C++, which
are two different languages. Telling us from the beginning which
language you're using would have been helpful; for example, we
wouldn't have bothered to suggest using "struct sockaddr_in" if
we had known you're using C++.

--
Keith Thompson (The_Other_Keith) kst-u(a)mib.org <http://www.ghoti.net/~kst>
Nokia
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"
From: Alf P. Steinbach on
* Andrew Falanga:
> Hi,
>
> Couple of disclaimers. I'm using VS2008 so the compiler errors come
> from that. Though I'm using the sockaddr_in structure in my code, and
> for this example, this question is not about socket programming.
>
> I have the following:
>
> sockaddr_in foo; // sockaddr_in is a struct for those not familiar
> foo.sin_port = 5075;
>
> int main() {
> // do some important stuff
> return 0;
> }
>
> In this form, I get the following errors:
> error C2143: syntax error : missing ';' before '.'
> error C4430: missing type specifier - int assumed.
> error C2371: 'foo' : redefinition; different basic types
>
> What's interesting is that *BEFORE* I place that assignment of 5075 to
> foo.sin_port and I hover over the object named foo, IntelliSense sees
> it as an object of type sockaddr_in. However, after I make that
> assignment, IntelliSense says that foo is an object of type int. If
> the assignment is moved to inside the body of main( ), there's no
> problem. The compiler is happy.
>
> I know I'm violating some language constraint but I can't remember
> what

He he :-) It's this: you can't have a non-declaration statement, what I call a
"command", outside of a routine.

There are a number of solutions to your quandary.

First, in C style, except using C++ references, you can do

sockaddr_in& the_foo()
{
static sockaddr_in a = {}; // Zero everything
if( a.sin_port == 0 ) { a.sin_port = 5075; }
return a;
}

int main()
{
sockaddr_in& foo = the_foo();
// Use foo here.
}

Better, but requiring more knowledge of C++, you can derive a class with custom
construction:

struct Foo: sockaddr_in
{
explicit Foo( int const a_sin_port )
: sockaddr_in() // Zero everything
{
sin_port = a_sin_port;
}
};

int main()
{
Foo foo( 5075 );
// Use foo here.
}


Cheers & hth.,

- Alf
From: Andrew Falanga on
On Feb 24, 11:23 am, "Alf P. Steinbach" <al...(a)start.no> wrote:
> * Andrew Falanga:
>
>
>
> > Hi,
>
> > Couple of disclaimers.  I'm using VS2008 so the compiler errors come
> > from that.  Though I'm using the sockaddr_in structure in my code, and
> > for this example, this question is not about socket programming.
>
> > I have the following:
>
> > sockaddr_in foo;  // sockaddr_in is a struct for those not familiar
> > foo.sin_port = 5075;
>
> > int main() {
> >    // do some important stuff
> >    return 0;
> > }
>
> > In this form, I get the following errors:
> > error C2143: syntax error : missing ';' before '.'
> > error C4430: missing type specifier - int assumed.
> > error C2371: 'foo' : redefinition; different basic types
>
> > What's interesting is that *BEFORE* I place that assignment of 5075 to
> > foo.sin_port and I hover over the object named foo, IntelliSense sees
> > it as an object of type sockaddr_in.  However, after I make that
> > assignment, IntelliSense says that foo is an object of type int.  If
> > the assignment is moved to inside the body of main( ), there's no
> > problem.  The compiler is happy.
>
> > I know I'm violating some language constraint but I can't remember
> > what
>
> He he :-) It's this: you can't have a non-declaration statement, what I call a
> "command", outside of a routine.
>
> There are a number of solutions to your quandary.
>
> First, in C style, except using C++ references, you can do
>
>    sockaddr_in& the_foo()
>    {
>        static sockaddr_in a = {};    // Zero everything
>        if( a.sin_port == 0 ) { a.sin_port = 5075; }
>        return a;
>    }
>
>    int main()
>    {
>        sockaddr_in& foo = the_foo();
>        // Use foo here.
>    }
>
> Better, but requiring more knowledge of C++, you can derive a class with custom
> construction:
>
>    struct Foo: sockaddr_in
>    {
>        explicit Foo( int const a_sin_port )
>            : sockaddr_in()    // Zero everything
>        {
>            sin_port = a_sin_port;
>        }
>    };
>
>    int main()
>    {
>        Foo foo( 5075 );
>        // Use foo here.
>    }
>
> Cheers & hth.,
>
> - Alf

Thanks to everyone. I had noticed that it ok within the main
function. I was figuring it had something to do with that, but I'm
not able to devote the bulk of my time to C++ programming and was just
not remembering why that was not working. It simply is the assignment
outside of the function body.

Thanks again everyone.

Andy