Ivan Perisic scored early in the second half to put Croatia ahead of Portugal in their World Cup Round of 32 match in Toronto.
The 37-year-old former Tottenham winger, now at PSV Eindhoven, collected the ball unmarked at the back post and fired past goalkeeper Diogo Costa.
Portugal had dominated possession in the first half but managed only one shot on target from nine attempts. Cristiano Ronaldo came close with several headers but had one goal ruled out for offside.
Bruno Fernandes also had two chances denied for the Portuguese side. Croatia, less dominant early on, celebrated wildly after taking the lead with support from outnumbered fans in the stadium.
Ronaldo and his teammates now need a comeback to avoid a shock exit in the first knockout round.