Jump to content
  • Advertisement
Sign in to follow this  
Dentoid

Operator problems

This topic is 4696 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

Hey Long time since I posted anything here, and unfortunately now when I do it's because I'm having problems. I've got this C++ class "csVector3" that is a standard vector (in the geometrical sense) class. It's got three members:
      /// The X component of the vector
      float x;
      /// The Y component of the vector
      float y;
      /// The Z component of the vector
      float z;
Also, it has a bunch of operators, with the most important beeing:
  /// Add two vectors.
  inline friend csVector3 operator+(const csVector3& v1, const csVector3& v2)
    { return csVector3(v1.x+v2.x, v1.y+v2.y, v1.z+v2.z); }

  /// Subtract two vectors.
  inline friend csVector3 operator-(const csVector3& v1, const csVector3& v2)
    { return csVector3(v1.x-v2.x, v1.y-v2.y, v1.z-v2.z); }

  /// Multiply a vector and a scalar.
  inline friend csVector3 operator* (const csVector3& v, float f)
    { return csVector3(v.x*f, v.y*f, v.z*f); }

  /// Multiply a vector and a scalar.
  inline friend csVector3 operator* (float f, const csVector3& v)
    { return csVector3(v.x*f, v.y*f, v.z*f); }

  /// Divide a vector by a scalar int.
  inline friend csVector3 operator/ (const csVector3& v, int f)
    { return v / (float)f; }

  /// Multiply this vector by a scalar.
  inline csVector3& operator*= (float f)
    { x *= f; y *= f; z *= f; return *this; }

  /// Divide this vector by a scalar.
  inline csVector3& operator/= (float f)
    { f = 1.0f / f; x *= f; y *= f; z *= f; return *this; }

  /// Add another vector to this vector.
  inline csVector3& operator+= (const csVector3& v)
  {
    x += v.x;
    y += v.y;
    z += v.z;

    return *this;
  }

  /// Subtract another vector from this vector.
  inline csVector3& operator-= (const csVector3& v)
  {
    x -= v.x;
    y -= v.y;
    z -= v.z;
    return *this;
  }
It's also got a couple of constructors, but no destructor or assignments. I register this class to AngelScript like this:
    engine->RegisterObjectType ("Vector3", sizeof (csVector3), asOBJ_CLASS_C);
    engine->RegisterObjectProperty ("Vector3", "float x", offsetof(csVector3, x));
    engine->RegisterObjectProperty ("Vector3", "float y", offsetof(csVector3, y));
    engine->RegisterObjectProperty ("Vector3", "float z", offsetof(csVector3, z));
    engine->RegisterObjectBehaviour ("Vector3", asBEHAVE_CONSTRUCT, "void f()", asFUNCTIONPR(ConstructVector3, (csVector3*), void), asCALL_CDECL_OBJLAST);

    engine->RegisterObjectBehaviour ("Vector3", asBEHAVE_CONSTRUCT, "void f(float, float, float)", asFUNCTIONPR(ConstructVector3, (float, float, float, csVector3*), void), asCALL_CDECL_OBJLAST);

    engine->RegisterObjectMethod ("Vector3", "float Length()", asMETHODPR(csVector3, Norm, (void) const, float), asCALL_THISCALL);

    engine->RegisterObjectMethod ("Vector3", "void Normalize()", asMETHOD(csVector3, Normalize), asCALL_THISCALL);

    engine->RegisterGlobalBehaviour (asBEHAVE_ADD, "Vector3 f(Vector3 &in, Vector3 &in)", asFUNCTIONPR(operator+, (const csVector3&, const csVector3&), csVector3), asCALL_CDECL);

    engine->RegisterGlobalBehaviour (asBEHAVE_SUBTRACT, "Vector3 f(Vector3 &in, Vector3 &in)", asFUNCTIONPR(operator-, (const csVector3&, const csVector3&), csVector3), asCALL_CDECL);

    engine->RegisterGlobalBehaviour (asBEHAVE_MULTIPLY, "Vector3 f(Vector3 &in, float)", asFUNCTIONPR(operator*, (const csVector3&, float), csVector3), asCALL_CDECL);

    engine->RegisterGlobalBehaviour (asBEHAVE_MULTIPLY, "Vector3 f(float, Vector3 &in)", asFUNCTIONPR(operator*, (float, const csVector3&), csVector3), asCALL_CDECL);

    engine->RegisterGlobalBehaviour (asBEHAVE_DIVIDE, "Vector3 f(Vector3 &in, float)", asFUNCTIONPR(operator/, (const csVector3&, float), csVector3), asCALL_CDECL);

    engine->RegisterObjectBehaviour ("Vector3", asBEHAVE_ADD_ASSIGN, "Vector3 &f(Vector3 &in)", asMETHODPR(csVector3, operator+=, (const csVector3&), csVector3&), asCALL_THISCALL);

    engine->RegisterObjectBehaviour ("Vector3", asBEHAVE_SUB_ASSIGN, "Vector3 &f(Vector3 &in)", asMETHODPR(csVector3, operator+=, (const csVector3&), csVector3&), asCALL_THISCALL);

    engine->RegisterObjectBehaviour ("Vector3", asBEHAVE_MUL_ASSIGN, "Vector3 &f(float)", asMETHODPR(csVector3, operator*=, (float), csVector3&), asCALL_THISCALL);

    engine->RegisterObjectBehaviour ("Vector3", asBEHAVE_DIV_ASSIGN, "Vector3 &f(float)", asMETHODPR(csVector3, operator/=, (float), csVector3&), asCALL_THISCALL);
Okay, so now to my problems. When using this class, I sometimes get crashes in the operators. I've got a line like this:
if(something) {
...
Vector3 newPos1 = meshOrigin + sideVector*0.1f + frontVector*stepLength;
...
} else {
...
}
Here all variables except stepLength are Vector3s, while stepLength is a float. It crashes in the first addition. (v1 in operator+ becomes a broken reference, null). If I for example remove the "sideVector*0.1f" it works. Also if I move the calculation outside the "if" it works. It also works if I split it up to:
   Vector3 newPos2 = meshOrigin;
   newPos2 += sideVector*0.1f;
   newPos2 += frontVector*stepLength;
So basically if you shuffle it around a bit or so you might get lucky. Maybe I've done something wrong somewhere, but I've checked my configuration a lot and it seems correct to me. So, I think there might be something wrong in how operators work in some cases, but I haven't been able to identify the exact circumstances. I realize this may be a bit thin info, but it's all I can give right now I think. Any ideas whatsoever? Thanks /Anders EDIT: Changed the subject, since I accidentally left it as "Untitled". [Edited by - Dentoid on October 10, 2005 9:22:22 AM]

Share this post


Link to post
Share on other sites
Advertisement
Holy redundant comments batman!

Your C++ operators return references. You tell angelscript they return by value.

Share this post


Link to post
Share on other sites
Quote:
Original post by Deyja
Holy redundant comments batman!

Your C++ operators return references. You tell angelscript they return by value.


Unless I'm overlooking something silly, only the assignment operators return references, the others return by value.

Share this post


Link to post
Share on other sites
Indeed, I cannot see anything wrong in your registration.

From your description it sounds like a problem with the AngelScript compiler. I guess it is either reusing a temporary variable that it shouldn't, or it is releasing a temporary too early. By splitting the expression into several statements, you should be able to avoid this problem.

I will look into this, as soon as possible. I'll stop working on 2.5.0 for a while and fix all the reported bugs for 2.4.1.



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.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!