Videos
Straight from the relevant portion of the ECMAScript 6 spec:
If Type(value) is Object and value has a [[DateValue]] internal slot, then Let tv be thisTimeValue(value).
Which basically says that if you pass the Date constructor a single argument and it's an object and it has the [[DateValue]] internal slot, then use that to initialize the new object.
So, what you are seeing is documented in the specification.
Here's more detail:

But, the ES5 spec is not the same and will do a conversion to a string when you do what you're doing which will then be parsed as a string by the constructor. While that will work to preserve everything down to the seconds, it will not preserve milliseconds since those are not present in the default string conversion. So, if you want a perfect copy, then you should do this in ES5 or earlier:
var date = new Date();
var date2 = new Date(date.getTime());
I would advise against that for now. This is what's going now under the browsers following different specs for the Date object.
ES 6.0:
var d1 = new Date();
var d2 = new Date(d1.getTime());
//ES6.0 basically gets the property that holds the timestamp straight from the object.
document.getElementById('results').innerHTML = 'Assert: ' + d1.valueOf() + ' === ' + d2.valueOf() + ' ' + (d1.valueOf() === d2.valueOf());
<pre id="results"></pre>
It does compare it perfectly BUT.... Here's how ES5.1 will handle that:
var d1 = new Date();
var d2 = new Date(Date.parse(d1.toString()));
//ES5.1 will attempt to parse the string representation of the Date object.
document.getElementById('results').innerHTML = 'Assert: ' + d1.valueOf() + ' === ' + d2.valueOf() + ' ' + (d1.valueOf() === d2.valueOf());
<pre id="results"></pre>
It basically gets rids of the milliseconds of the first Date object (Assertion might work if the first date object has no milliseconds, run the snippet a couple of times). Firefox seems to be following ES5.1 behaviour at the moment and Chrome ES6.0. Can't really say when they started adopting it.
I would definately not advise to pass the Date object as a constructor for a new Date object if the purpose is to clone the first Date object. Use Data.prototype.getTime() instead.
It is the definition of the Date object to use values 0-11 for the month field.
I believe that the constructor using a String is system-dependent (not to mention locale/timezone dependent) so you are probably better off using the constructor where you specify year/month/day as separate parameters.
BTW, in Firefox,
new Date("04/02/2008");
It works fine for me - it will interpret slashes, but not hyphens. This proves my point that using a String to construct a Date object is problematic. Use explicit values for month/day/year instead:
new Date(2008, 3, 2);
nice trick indeed, which I just found out the hard way (by thinking through it). But I used a more natural date string with a hyphen :-)
var myDateArray = "2008-03-02".split("-");
var theDate = new Date(myDateArray[0],myDateArray[1]-1,myDateArray[2]);
alert(theDate);