@@ -24,17 +24,17 @@ namespace {
2424// High-level structure to track info needed to emit a
2525// sframe_frame_row_entry_addrX. On disk these have both a fixed portion of type
2626// sframe_frame_row_entry_addrX and trailing data of X * S bytes, where X is the
27- // datum size, and S is 1, 2, or 3 depending on which of Cfa , SP, and FP are
27+ // datum size, and S is 1, 2, or 3 depending on which of CFA , SP, and FP are
2828// being tracked.
2929struct SFrameFRE {
3030 // An FRE describes how to find the registers when the PC is at this
3131 // Label from function start.
3232 const MCSymbol *Label = nullptr ;
33- size_t CfaOffset = 0 ;
33+ size_t CFAOffset = 0 ;
3434 size_t FPOffset = 0 ;
3535 size_t RAOffset = 0 ;
3636 bool FromFP = false ;
37- bool CfaRegSet = false ;
37+ bool CFARegSet = false ;
3838
3939 SFrameFRE (const MCSymbol *Start) : Label(Start) {}
4040};
@@ -46,13 +46,11 @@ struct SFrameFDE {
4646 const MCDwarfFrameInfo &DFrame;
4747 // Label where this FDE's FREs start.
4848 MCSymbol *FREStart;
49- // True when unwind info can't be described with an Sframe FDE.
50- bool Invalid;
5149 // Unwinding fres
5250 SmallVector<SFrameFRE> FREs;
5351
5452 SFrameFDE (const MCDwarfFrameInfo &DF, MCSymbol *FRES)
55- : DFrame(DF), FREStart(FRES), Invalid( false ) {}
53+ : DFrame(DF), FREStart(FRES) {}
5654
5755 void emit (MCObjectStreamer &S, const MCSymbol *FRESubSectionStart) {
5856 MCContext &C = S.getContext ();
@@ -109,91 +107,81 @@ class SFrameEmitterImpl {
109107 MCSymbol *FRESubSectionStart;
110108 MCSymbol *FRESubSectionEnd;
111109
112-
113- bool setCfaRegister (SFrameFDE &FDE, SFrameFRE &FRE, const MCCFIInstruction &I) {
110+ bool setCFARegister (SFrameFRE &FRE, const MCCFIInstruction &I) {
114111 if (I.getRegister () == SPReg) {
115- FRE.CfaRegSet = true ;
112+ FRE.CFARegSet = true ;
116113 FRE.FromFP = false ;
117114 return true ;
118- } else if (I.getRegister () == FPReg) {
119- FRE.CfaRegSet = true ;
115+ }
116+ if (I.getRegister () == FPReg) {
117+ FRE.CFARegSet = true ;
120118 FRE.FromFP = true ;
121119 return true ;
122120 }
123121 Streamer.getContext ().reportWarning (
124122 I.getLoc (), " Canonical Frame Address not in stack- or frame-pointer. "
125123 " Omitting SFrame unwind info for this function." );
126- FDE.Invalid = true ;
127124 return false ;
128125 }
129126
130- bool isCfaRegisterSet (SFrameFDE &FDE, SFrameFRE &FRE,
131- const MCCFIInstruction &I) {
132- if (FRE.CfaRegSet )
133- return true ;
134-
135- Streamer.getContext ().reportWarning (
136- I.getLoc (), " Adjusting CFA offset without a base register. "
137- " Omitting SFrame unwind info for this function." );
138- FDE.Invalid = true ;
139- return false ;
127+ bool setCFAOffset (SFrameFRE &FRE, const SMLoc &Loc, size_t Offset) {
128+ if (!FRE.CFARegSet ) {
129+ Streamer.getContext ().reportWarning (
130+ Loc, " Adjusting CFA offset without a base register. "
131+ " Omitting SFrame unwind info for this function." );
132+ return false ;
133+ }
134+ FRE.CFAOffset = Offset;
135+ return true ;
140136 }
141137
142138 // Add the effects of CFI to the current FDE, creating a new FRE when
143139 // necessary.
144- void handleCFI (SFrameFDE &FDE, SFrameFRE &FRE, const MCCFIInstruction &CFI) {
140+ bool handleCFI (SFrameFDE &FDE, SFrameFRE &FRE, const MCCFIInstruction &CFI) {
145141 switch (CFI.getOperation ()) {
146142 case MCCFIInstruction::OpDefCfaRegister:
147- setCfaRegister (FDE, FRE, CFI);
148- return ;
143+ return setCFARegister (FRE, CFI);
149144 case MCCFIInstruction::OpDefCfa:
150145 case MCCFIInstruction::OpLLVMDefAspaceCfa:
151- if (!setCfaRegister (FDE, FRE, CFI))
152- return ;
153- FRE. CfaOffset = CFI.getOffset ();
154- return ;
146+ if (!setCFARegister ( FRE, CFI))
147+ return false ;
148+ setCFAOffset ( FRE, CFI. getLoc (), CFI.getOffset () );
149+ return true ;
155150 case MCCFIInstruction::OpOffset:
156151 if (CFI.getRegister () == FPReg)
157152 FRE.FPOffset = CFI.getOffset ();
158153 else if (CFI.getRegister () == RAReg)
159154 FRE.RAOffset = CFI.getOffset ();
160- return ;
155+ return true ;
161156 case MCCFIInstruction::OpRelOffset:
162157 if (CFI.getRegister () == FPReg)
163158 FRE.FPOffset += CFI.getOffset ();
164159 else if (CFI.getRegister () == RAReg)
165160 FRE.RAOffset += CFI.getOffset ();
166- return ;
161+ return true ;
167162 case MCCFIInstruction::OpDefCfaOffset:
168- if (!isCfaRegisterSet (FDE, FRE, CFI))
169- return ;
170- FRE.CfaOffset = CFI.getOffset ();
171- return ;
163+ return setCFAOffset (FRE, CFI.getLoc (), CFI.getOffset ());
172164 case MCCFIInstruction::OpAdjustCfaOffset:
173- if (!isCfaRegisterSet (FDE, FRE, CFI))
174- return ;
175- FRE.CfaOffset += CFI.getOffset ();
176- return ;
165+ return setCFAOffset (FRE, CFI.getLoc (), FRE.CFAOffset + CFI.getOffset ());
177166 case MCCFIInstruction::OpRememberState:
178- // TODO: Implement
179- return ;
167+ // TODO: Implement. Will use FDE.
168+ return true ;
180169 case MCCFIInstruction::OpRestore:
181- // TODO: Implement
182- return ;
170+ // TODO: Implement. Will use FDE.
171+ return true ;
183172 case MCCFIInstruction::OpRestoreState:
184- // TODO: Implement
185- return ;
173+ // TODO: Implement. Will use FDE.
174+ return true ;
186175 case MCCFIInstruction::OpEscape:
187- // TODO: Implement
188- return ;
176+ // TODO: Implement. Will use FDE.
177+ return true ;
189178 default :
190- // Instructions that don't affect the Cfa , RA, and SP can be safely
179+ // Instructions that don't affect the CFA , RA, and SP can be safely
191180 // ignored.
192- return ;
181+ return true ;
193182 }
194183 }
195184
196-
197185public:
198186 SFrameEmitterImpl (MCObjectStreamer &Streamer) : Streamer(Streamer) {
199187 assert (Streamer.getContext ()
@@ -230,13 +218,14 @@ class SFrameEmitterImpl {
230218 }
231219
232220 bool equalIgnoringLocation (const SFrameFRE &Left, const SFrameFRE &Right) {
233- return Left.CfaOffset == Right.CfaOffset &&
221+ return Left.CFAOffset == Right.CFAOffset &&
234222 Left.FPOffset == Right.FPOffset && Left.RAOffset == Right.RAOffset &&
235- Left.FromFP == Right.FromFP && Left.CfaRegSet == Right.CfaRegSet ;
223+ Left.FromFP == Right.FromFP && Left.CFARegSet == Right.CFARegSet ;
236224 }
237225
238226 void buildSFDE (const MCDwarfFrameInfo &DF) {
239- auto &FDE = FDEs.emplace_back (DF, Streamer.getContext ().createTempSymbol ());
227+ bool Valid = true ;
228+ SFrameFDE FDE (DF, Streamer.getContext ().createTempSymbol ());
240229 // This would have been set via ".cfi_return_column", but
241230 // MCObjectStreamer doesn't emit an MCCFIInstruction for that. It just
242231 // sets the DF.RAReg.
@@ -245,18 +234,18 @@ class SFrameEmitterImpl {
245234 // hand-written assembly.
246235 if (DF.RAReg != RAReg) {
247236 Streamer.getContext ().reportWarning (
248- SMLoc (), " Non-default RA register " + Twine (DF.RAReg ) +
237+ SMLoc (), " Non-default RA register in .cfi_return_column " +
238+ Twine (DF.RAReg ) +
249239 " . Omitting SFrame unwind info for this function." );
250- // Continue with the FDE to find any addtional errors. Discard it at
251- // the end.
252- FDE.Invalid = true ;
240+ Valid = false ;
253241 }
254- MCSymbol *BaseLabel = DF.Begin ;
255- SFrameFRE BaseFRE (BaseLabel );
242+ MCSymbol *LastLabel = DF.Begin ;
243+ SFrameFRE BaseFRE (LastLabel );
256244 if (!DF.IsSimple ) {
257245 for (const auto &CFI :
258246 Streamer.getContext ().getAsmInfo ()->getInitialFrameState ())
259- handleCFI (FDE, BaseFRE, CFI);
247+ if (!handleCFI (FDE, BaseFRE, CFI))
248+ Valid = false ;
260249 }
261250 FDE.FREs .push_back (BaseFRE);
262251
@@ -269,24 +258,25 @@ class SFrameEmitterImpl {
269258 continue ;
270259
271260 SFrameFRE FRE = FDE.FREs .back ();
272- handleCFI (FDE, FRE, CFI);
261+ if (!handleCFI (FDE, FRE, CFI))
262+ Valid = false ;
273263
274264 // If nothing relevant but the location changed, don't add the FRE.
275265 if (equalIgnoringLocation (FRE, FDE.FREs .back ()))
276266 continue ;
277267
278268 // If the location stayed the same, then update the current
279269 // row. Otherwise, add a new one.
280- if (atSameLocation (BaseLabel , L))
270+ if (atSameLocation (LastLabel , L))
281271 FDE.FREs .back () = FRE;
282272 else {
283273 FDE.FREs .push_back (FRE);
284274 FDE.FREs .back ().Label = L;
285- BaseLabel = L;
275+ LastLabel = L;
286276 }
287277 }
288- if (FDE. Invalid )
289- FDEs.pop_back ( );
278+ if (Valid )
279+ FDEs.push_back (FDE );
290280 }
291281
292282 void emitPreamble () {
@@ -309,8 +299,6 @@ class SFrameEmitterImpl {
309299 Streamer.emitInt32 (FDEs.size ());
310300 // shf_num_fres
311301 uint32_t TotalFREs = 0 ;
312- // for (auto &FDE : FDEs)
313- // TotalFREs += FDE.FREs.size();
314302 Streamer.emitInt32 (TotalFREs);
315303
316304 // shf_fre_len
0 commit comments