Jump to content
  • Advertisement
Sign in to follow this  
jamesleighe

Assembly Question

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

I'm trying to see how the compiler optimizes certain code.

I comment out one 'unit' and compile it, check the assembly, and do the same for the other one.

int main( )
{
// UNIT 1

float a1, b1, c1, d1, e1, f1;
std::cin>> a1;
std::cin>> b1;
std::cin>> c1;
std::cin>> d1;
std::cin>> e1;
std::cin>> f1;
Vector3D resultA = Vector3D( a1, b1, c1 ) + Vector3D( d1, e1, f1 );
std::cout<< resultA.x;
std::cout<< resultA.y;
std::cout<< resultA.z;

// UNIT 2
/*
float a2, b2, c2, d2, e2, f2;
std::cin>> a2;
std::cin>> b2;
std::cin>> c2;
std::cin>> d2;
std::cin>> e2;
std::cin>> f2;
Vector3D resultB;
VectorAdd( a2, b2, c2, d2, e2, f2, resultB );
std::cout<< resultB.x;
std::cout<< resultB.y;
std::cout<< resultB.z;
*/

return 0;
}


But, it seems to be generating strange assembly for 'unit 1' (truncated):


Vector3D resultA = Vector3D( a1, b1, c1 ) + Vector3D( d1, e1, f1 );
010E1066 fld dword ptr [f1]
010E1069 fadd dword ptr [c1]
std::cout<< resultA.x;
010E106C push ecx
010E106D mov ecx,dword ptr [__imp_std::cout (10E2050h)]
010E1073 fstp dword ptr [resultA]
010E1076 fld dword ptr [resultA]
010E1079 fstp dword ptr [esp]
010E107C call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (10E204Ch)]
std::cout<< resultA.y;
010E1082 fld dword ptr [ebp-38h]
010E1085 push ecx
010E1086 mov ecx,dword ptr [__imp_std::cout (10E2050h)]
010E108C fstp dword ptr [esp]
010E108F call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (10E204Ch)]
std::cout<< resultA.z;
010E1095 fld dword ptr [ebp-34h]
010E1098 push ecx
010E1099 mov ecx,dword ptr [__imp_std::cout (10E2050h)]
010E109F fstp dword ptr [esp]
010E10A2 call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (10E204Ch)]


How can it be calling fadd only once? The assambly for unit 2 calls fadd 3 times, which is correct, but unit 1 seems to only call it once!

I'm not super good at assembly (i'm horrible actually), so what's going on here?

Thanks!!

Share this post


Link to post
Share on other sites
Advertisement
Could you post the complete C++ program you are running, and perhaps the complete assembly output? Also, what compiler is doing this?

Share this post


Link to post
Share on other sites
MSVC is the compiler, set to Release mode with default settings.

Complete source (note that only one unit is compiled at a time and the other is commented out):


#include <iostream>

class Vector3D
{
public:
Vector3D( )
{
;
}

Vector3D( float _x, float _y, float _z )
{
x = _x;
y = _y;
z = _z;
}

Vector3D( const Vector3D& vector )
{
x = vector.x;
x = vector.y;
x = vector.z;
}

Vector3D& operator+( const Vector3D& vector )
{
x += vector.x;
y += vector.y;
z += vector.z;
return *this;
}

float x;
float y;
float z;
};

void VectorAdd( float a, float b, float c, float d, float e, float f, Vector3D& dest )
{
dest.x = a + d;
dest.y = b + e;
dest.z = c + f;
}

void VectorAdd( const Vector3D& a, const Vector3D& b, Vector3D& dest )
{
dest.x = a.x + b.x;
dest.y = a.y + b.y;
dest.z = a.z + b.z;
}

int main( )
{
// UNIT 1

float a1, b1, c1, d1, e1, f1;
std::cin>> a1;
std::cin>> b1;
std::cin>> c1;
std::cin>> d1;
std::cin>> e1;
std::cin>> f1;
Vector3D resultA = Vector3D( a1, b1, c1 ) + Vector3D( d1, e1, f1 );
std::cout<< resultA.x;
std::cout<< resultA.y;
std::cout<< resultA.z;

// UNIT 2
/*
float a2, b2, c2, d2, e2, f2;
std::cin>> a2;
std::cin>> b2;
std::cin>> c2;
std::cin>> d2;
std::cin>> e2;
std::cin>> f2;
Vector3D resultB;
VectorAdd( a2, b2, c2, d2, e2, f2, resultB );
std::cout<< resultB.x;
std::cout<< resultB.y;
std::cout<< resultB.z;
*/

return 0;
}


Complete assembly for unit 1:


int main( )
{
01061000 push ebp
01061001 mov ebp,esp
01061003 sub esp,24h
// UNIT 1

float a1, b1, c1, d1, e1, f1;
std::cin>> a1;
01061006 mov ecx,dword ptr [__imp_std::cin (1062048h)]
0106100C lea eax,[a1]
0106100F push eax
01061010 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (1062044h)]
std::cin>> b1;
01061016 lea ecx,[b1]
01061019 push ecx
0106101A mov ecx,dword ptr [__imp_std::cin (1062048h)]
01061020 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (1062044h)]
std::cin>> c1;
01061026 mov ecx,dword ptr [__imp_std::cin (1062048h)]
0106102C lea edx,[c1]
0106102F push edx
01061030 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (1062044h)]
std::cin>> d1;
01061036 mov ecx,dword ptr [__imp_std::cin (1062048h)]
0106103C lea eax,[d1]
0106103F push eax
01061040 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (1062044h)]
std::cin>> e1;
01061046 lea ecx,[e1]
01061049 push ecx
0106104A mov ecx,dword ptr [__imp_std::cin (1062048h)]
01061050 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (1062044h)]
std::cin>> f1;
01061056 mov ecx,dword ptr [__imp_std::cin (1062048h)]
0106105C lea edx,[f1]
0106105F push edx
01061060 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (1062044h)]
Vector3D resultA = Vector3D( a1, b1, c1 ) + Vector3D( d1, e1, f1 );
01061066 fld dword ptr [f1]
01061069 fadd dword ptr [c1]
std::cout<< resultA.x;
0106106C push ecx
0106106D mov ecx,dword ptr [__imp_std::cout (1062050h)]
01061073 fstp dword ptr [resultA]
01061076 fld dword ptr [resultA]
01061079 fstp dword ptr [esp]
0106107C call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (106204Ch)]
std::cout<< resultA.y;
01061082 fld dword ptr [ebp-20h]
01061085 push ecx
01061086 mov ecx,dword ptr [__imp_std::cout (1062050h)]
0106108C fstp dword ptr [esp]
0106108F call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (106204Ch)]
std::cout<< resultA.z;
01061095 fld dword ptr [ebp-1Ch]
01061098 push ecx
01061099 mov ecx,dword ptr [__imp_std::cout (1062050h)]
0106109F fstp dword ptr [esp]
010610A2 call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (106204Ch)]

return 0;
010610A8 xor eax,eax
}


Complete assembly for unit 2:


int main( )
{
002E1000 push ebp
002E1001 mov ebp,esp
002E1003 sub esp,24h

// UNIT 2
float a2, b2, c2, d2, e2, f2;
std::cin>> a2;
002E1006 mov ecx,dword ptr [__imp_std::cin (2E2048h)]
002E100C lea eax,[a2]
002E100F push eax
002E1010 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (2E2044h)]
std::cin>> b2;
002E1016 lea ecx,[b2]
002E1019 push ecx
002E101A mov ecx,dword ptr [__imp_std::cin (2E2048h)]
002E1020 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (2E2044h)]
std::cin>> c2;
002E1026 mov ecx,dword ptr [__imp_std::cin (2E2048h)]
002E102C lea edx,[c2]
002E102F push edx
002E1030 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (2E2044h)]
std::cin>> d2;
002E1036 mov ecx,dword ptr [__imp_std::cin (2E2048h)]
002E103C lea eax,[d2]
002E103F push eax
002E1040 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (2E2044h)]
std::cin>> e2;
002E1046 lea ecx,[e2]
002E1049 push ecx
002E104A mov ecx,dword ptr [__imp_std::cin (2E2048h)]
002E1050 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (2E2044h)]
std::cin>> f2;
002E1056 mov ecx,dword ptr [__imp_std::cin (2E2048h)]
002E105C lea edx,[f2]
002E105F push edx
002E1060 call dword ptr [__imp_std::basic_istream<char,std::char_traits<char> >::operator>> (2E2044h)]
Vector3D resultB;
VectorAdd( a2, b2, c2, d2, e2, f2, resultB );
002E1066 fld dword ptr [d2]
002E1069 fadd dword ptr [a2]
std::cout<< resultB.x;
002E106C push ecx
002E106D mov ecx,dword ptr [__imp_std::cout (2E2050h)]
002E1073 fstp dword ptr [resultB]
002E1076 fld dword ptr [e2]
002E1079 fadd dword ptr [b2]
002E107C fstp dword ptr [ebp-20h]
002E107F fld dword ptr [f2]
002E1082 fadd dword ptr [c2]
002E1085 fstp dword ptr [ebp-1Ch]
002E1088 fld dword ptr [resultB]
002E108B fstp dword ptr [esp]
002E108E call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (2E204Ch)]
std::cout<< resultB.y;
002E1094 fld dword ptr [ebp-20h]
002E1097 push ecx
002E1098 mov ecx,dword ptr [__imp_std::cout (2E2050h)]
002E109E fstp dword ptr [esp]
002E10A1 call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (2E204Ch)]
std::cout<< resultB.z;
002E10A7 fld dword ptr [ebp-1Ch]
002E10AA push ecx
002E10AB mov ecx,dword ptr [__imp_std::cout (2E2050h)]
002E10B1 fstp dword ptr [esp]
002E10B4 call dword ptr [__imp_std::basic_ostream<char,std::char_traits<char> >::operator<< (2E204Ch)]


return 0;
002E10BA xor eax,eax
}


Unit 2 has straightforward assembly output, unit 1 I can't seem to figure out how it's computing the result!

Share this post


Link to post
Share on other sites
Did it actually occur to you to run the program? You have typos in your copy constructor that prevent it from working correctly.

EDIT: Also, your operator + has the semantics I expect for operator += (i.e., it modifies the left-hand side).

Share this post


Link to post
Share on other sites
I just tested unit 1 and it's giving me wrong answers, only x (the one fadd that is called to compute) is correct.

So I just wrote bad code it seems!

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!