Just to add to the other answers talking about IEEE-754 and x86:  the issue is even more complicated than they make it seem.  There is not "one" representation of 0.1 in IEEE-754 - there are two.  Either rounding the last digit down or up would be valid.  This difference can and does actually occur, because x86 does not use 64-bits for its internal floating-point computations; it actually uses 80-bits!  This is called double extended-precision.
So, even among just x86 compilers, it sometimes happen that the same number is represented two different ways, because some computes its binary representation with 64-bits, while others use 80.
In fact, it can happen even with the same compiler, even on the same machine!
#include <iostream>
#include <cmath>
void foo(double x, double y)
{
  if (std::cos(x) != std::cos(y)) {
    std::cout << "Huh?!?\n";  //← you might end up here when x == y!!
  }
}
int main()
{
  foo(1.0, 1.0);
  return 0;
}
See Why is cos(x) != cos(y) even though x == y? for more info.