Jump to content
  • Advertisement
Sign in to follow this  
clashie

missing type specifier, why?

This topic is 2914 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

#pragma once
#include "math.h"
#include "vector.h"

namespace bnr {
namespace math {
//////////////////////////////////////////////////////////////////////////
struct Matrix
{
void zero ();
void copy (const Matrix& m);

void identity ();
void perspective(f32 fovy, f32 aspect, f32 zn, f32 zf);

void add (const Matrix& m);
void subtract (const Matrix& m);
void multiply (const Matrix& m);
void divide (const Matrix& m);

void scale (const Vector& v);
void scale (f32 x, f32 y, f32 z);
void translate (const Vector& v);
void translate (f32 x, f32 y, f32 z);
void rotate (f32 x, f32 y, f32 z, f32 a);
void rotateX (f32 a);
void rotateY (f32 a);
void rotateZ (f32 a);

__declspec(align(16)) union
{
struct
{
f32 _11, _12, _13, _14,
_21, _22, _23, _24,
_31, _32, _33, _34,
_41, _42, _43, _44;
};

f32 m[4][4];
__m128 m128[4];
};
};
//////////////////////////////////////////////////////////////////////////
inline void Matrix::zero() { memset(this->m, 0, 64); }
inline void Matrix::copy(const Matrix& m) { memcpy(this->m, m.m, 64); }

... hundreds of lines of other functions...

}}



#pragma once
#include "math.h"
#include "matrix.h"

namespace bnr {
namespace math {
//////////////////////////////////////////////////////////////////////////
struct Vector
{
Vector() : x(0.0f), y(0.0f), z(0.0f), w(1.0f) { };
Vector(f32 xp, f32 yp, f32 zp) : x(xp), y(yp), z(zp), w(1.0f) { };
Vector(f32 xp, f32 yp, f32 zp, f32 wp) : x(xp), y(yp), z(zp), w(wp) { };

void multiply (const Matrix& m);
void multiply (const Vector& v, const Matrix& m);

__declspec(align(16)) union
{
struct{ f32 x, y, z, w; };
f32 v[4];
__m128 v128;
};
};
//////////////////////////////////////////////////////////////////////////
inline void Vector::multiply(const Matrix& m) { this->multiply(*this, m); }

inline void Vector::multiply(const Vector& v, const Matrix& m)
{
__m128 vx = _mm_shuffle_ps(v.v128, v.v128, 0x00); //broadcasts
__m128 vy = _mm_shuffle_ps(v.v128, v.v128, 0x55);
__m128 vz = _mm_shuffle_ps(v.v128, v.v128, 0xAA);
__m128 vw = _mm_shuffle_ps(v.v128, v.v128, 0xFF);

vx = _mm_mul_ps(vx, m.m128[0]);
vy = _mm_mul_ps(vy, m.m128[1]);
vz = _mm_mul_ps(vz, m.m128[2]);
vw = _mm_mul_ps(vw, m.m128[3]);

vx = _mm_add_ps(vx, vy);
vx = _mm_add_ps(vx, vz);
this->v128 = _mm_add_ps(vx, vw);
}
//////////////////////////////////////////////////////////////////////////
}}




first error points here:
void multiply	(const Matrix& m);


error C4430: missing type specifier - int assumed. Note: C++ does not support default-int
syntax error : missing ',' before '&'

and 20 other repeating errors for every instance of Matrix within the header. I don't get it, what am I missing?

Share this post


Link to post
Share on other sites
Advertisement
Vector.h includes Matrix.h which includes Vector.h which includes Matrix.h which includes Vector.h ...

You already recognized this and "solved" it by putting this pragma_once in there. But this only leads to a situation where e.g. Matrix.h includes Vector.h. Then, the compiler cannot compile Vector because this class definition uses the Matrix objects who's header he cannot include and read because you are actual inside the Matrix.h header.

Basically the rule is that not both objects can use instances of each other inside the header as references, only as pointers. To solve your problem remove all Matrix usage out of the Vector header. Then define * operators for the Vector Matrix multiplication outside of the Vector class inside the Matrix header.

Share this post


Link to post
Share on other sites
Tell me there's another work around, because I kinda like the way I have stuff laid out now. :(

Share this post


Link to post
Share on other sites
Quote:
Basically the rule is that not both objects can use instances of each other inside the header as references, only as pointers.
Unless I'm misinterpreting you, this statement is incorrect: references can be used with types that have been forward-declared, just as pointers can.
Quote:
Original post by clashie
Tell me there's another work around, because I kinda like the way I have stuff laid out now. :(
Well, when it comes to following the rules of the language, what we 'like' doesn't really matter that much :) But, you could try forward-declaring the types and moving the function definitions to separate source files. (They could no longer be marked as inline, but as I understand it, most compilers only consider 'inline' to be a suggestion anyway.)

Anyway, IMO at least, there's really no reason that a matrix class and a vector class need to have mutual knowledge of one another. Generally, functions that operate on both types (and binary operators in general) should be implemented as non-member functions, in which case they can be moved into their own headers. This is the usual approach, and unless you're dealing with unusual constraints of some sort, it's the approach I'd recommend.

Share this post


Link to post
Share on other sites
If you really want to keep the inline functions in the headers you can organize your headers like this:

matrix.h:

forward declare vector
matrix class definition
#include "vector.h"
inline function definitions

vector.h

forward declare matrix
vector class definition
#include "matrix.h"
inline function definitions

Share this post


Link to post
Share on other sites
Quote:
Original post by SiCrane
If you really want to keep the inline functions in the headers you can organize your headers like this:

matrix.h:

forward declare vector
matrix class definition
#include "vector.h"
inline function definitions

vector.h

forward declare matrix
vector class definition
#include "matrix.h"
inline function definitions


This is what I ended up doing.

Is there a better way to define my inline functions?

Share this post


Link to post
Share on other sites
Quote:
Original post by jyk
Quote:
Basically the rule is that not both objects can use instances of each other inside the header as references, only as pointers.
Unless I'm misinterpreting you, this statement is incorrect: references can be used with types that have been forward-declared, just as pointers can.

Ups ... you're right, I was not thinking too much while typing. I wanted to refer this to the non reference usages of the undefined types only.

Thanks for poiting this flaw out.

Share this post


Link to post
Share on other sites
I am currently wondering why your structs have methods O_o (why no classes?)

However have you tried something like:
struct Vector;

struct Matrix
{
[...]
};


instead of including the header of Vector? I dunno if that will work but once I had an similar problem and there it solved it.

Share this post


Link to post
Share on other sites
Quote:
Original post by Spell
I am currently wondering why your structs have methods O_o (why no classes?)

However have you tried something like:
*** Source Snippet Removed ***

instead of including the header of Vector? I dunno if that will work but once I had an similar problem and there it solved it.


That's just a forward declaration for a struct and it works, as pointed out above, for pointers and references you use inside headers. It does not work, though, for actual instances of the class because the compiler does not know how much space to allocate for such an instances (as opposed to pointers and references).

So in this case it does not help because the multiply methods return actual class instances, not only pointers or references.

However, note that the actual problem is already solved as a combination of forward declarations and an include later in the header file as you can read above.

Share this post


Link to post
Share on other sites
Quote:
I am currently wondering why your structs have methods O_o (why no classes?)
Why shouldn't they have methods?

In C++, structs and classes are the same (aside from default privileges), so there's nothing to stop you from using structs as the OP has done.

Granted, it's somewhat contrary to the common convention of only using structs for PODs and other simple user-defined types, but that is, after all, just a convention.
Quote:
However have you tried something like:
*** Source Snippet Removed ***

instead of including the header of Vector? I dunno if that will work but once I had an similar problem and there it solved it.
That's already been discussed (as Waterwalker pointed out).

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

Participate in the game development conversation and more when you create an account on GameDev.net!

Sign me up!