Bayern, who had thrashed Arsenal 10-2 on aggregate to take their place in the last eight, went in front after 26 minutes through a bullet header from Arturo Vidal.
The Chile midfielder, though, wasted a chance to double the German club’s advantage in first-half stoppage time when he blasted a penalty over the crossbar after what looked a poor handball decision against Dani Carvajal.
Real were level two minutes into the second half when Ronaldo swept in a cross from Carvajal.
Bayern had to play the final 30 minutes a man down after Javi Martinez picked up two quick cautions.
And Ronaldo took his tally to 100 European goals when he stabbed the ball past Manuel Neuer in the 77th minute to leave Carlo Ancelotti’s men with it all to do in next week’s second leg back at the Bernabeu.
Bayern were missing Poland forward Robert Lewandowsi because of a shoulder injury, so Thomas Muller led the attack.
Real, unbeaten in the Champions League so far this season, had to do without defenders Raphael Varane and Pepe, who suffered a double rib fracture in Saturday’s 1-1 draw with city rivals Atletico. Fernandez Nacho came into the backline.
After a tense opening it was the visitors who went close in the 18th minute.
Toni Kroos sent in a deep centre from the right and Karim Benzema headed the ball down, which bounced back up over the dive of Neuer, who may just have got a touch as it went on to the crossbar.
It was Bayern, though, who took the lead on 25 minutes.
Thiago played in an outswinging corner from the right, which Vidal powered past Keylor Navas, the goalkeeper only able to push the ball into the roof of the net.
Bayern remained on the offensive, with Franck Ribery’s shot deflected behind and Vidal sending a header just wide before at the other end Kroos flashed a low drive past the post following a corner as Real looked to get back into the tie.
In first-half stoppage time, Bayern had a chance to extend their lead after Carvajal was adjudged to have blocked Ribery’s shot with his arm.
However, Vidal stepped up to blast the penalty high over the crossbar.
It proved a costly miss as Real were on level terms early in the second half.
Carvajal whipped a ball across the Bayern penalty area from the right, which Ronaldo clipped past Neuer into the far corner.
Now it was Real who took hold of possession, with Bayern struggling to mount any sort of sustained pressure.
In the 56th minute, Carvajal got away down the right and sent a ball into the six-yard box, which Gareth Bale met with a bullet header, but Neuer made a superb reaction save over the crossbar.
The Wales forward soon went off, replaced by Marco Asensio, with some suggestions it could be precautionary against an injury concern.
Bayern were reduced to 10 men just after the hour when Javi Martinez, who had only just been cautioned, tripped Ronaldo as the Portugal forward looked to get clear.
Italian referee Nicola Rizzoli was left with little option but to show the defensive midfielder a second yellow card followed by a red.
Real looked to make their extra man count, with Sergio Ramos whipping a 25-yard free-kick just wide following a handball by Ribery.
Neuer proved Bayern’s last line of defence twice in as many minutes when he first kicked away Benzema’s close-range effort and then got a strong hand to beat off Ronaldo’s point-blank effort.
The German, though, could do little to prevent Real taking the lead on 77 minutes when Ronaldo stabbed in a low cross from Asensio.
Real could have further extended their advantage as Marcelo’s shot from the left flew wide and Benzema’s angled effort and a header from Ramos were both correctly ruled out for offside.
Neuer, Lahm, Javi Martinez, Boateng, Alaba, Alonso (Bernat 63), Vidal, Robben, Thiago, Ribery (Douglas Costa 66), Muller (Coman 81).
Navas, Carvajal, Nacho, Sergio Ramos, Marcelo, Modric (Kovacic 90), Casemiro, Kroos, Bale (Marco 58), Benzema (Rodriguez 83), Ronaldo.
Nicola Rizzoli (Italy).