In compiler design, control-flow statements are translated to sequences of three-address-code (3AC) instructions a lot of which are jump statements. A 3AC instruction of the jumping type could be an unconditional jump in the form of a goto statement with a target label as its argument, such as

goto L1

or it may be a conditional jump in the form of an if statement, as in

if a < b goto L1

Now when the compiler generates a 3AC jump instruction, the target label is available to it in the form of an inherited attribute ( which I assume is a pointer to an object/structure and so we could think of it as a pointer to a variable ).

Now, the labels passed to say, an if-else statement as inherited attributes would also be then attached to certain target instructions after the if-else construct that used those labels has been translated.

Suppose, a label L1 has been used a lot of times before in constructs that have now been translated. Now suppose that label has to be attached to say a target assignment statement (the next instruction to be emitted) whose index is in the array of instructions is 137 (because there are 137 3AC instructions already stored in the quadruples array). Then at this point of time the variable L1 would get the value 137 and so all the earlier uses of L1 would also now get the value of L1 (because the variable pointed to by them now gets a value).

And so in this way we have translated control-flow statements in one pass and there is no need for backpatching to reduce the number of passes further.

I don’t understand why what I just wrote wouldn’t work and without backpatching two passes would be required to attach labels to their correct instructions.

  • $\begingroup$ Your text is a bit hard to read. Can you break it into shorter paragraphs? $\endgroup$ – Yuval Filmus Apr 15 '20 at 17:47
  • $\begingroup$ @YuvalFilmus Ok I have shortened it. I just wanted to be as clear and detailed as possible and so I wrote too much. $\endgroup$ – Shashank Kumar Apr 15 '20 at 17:52
  • $\begingroup$ What if L1 appears after the goto L1 instruction? $\endgroup$ – Yuval Filmus Apr 15 '20 at 18:07
  • $\begingroup$ @YuvalFilmus Once you reach L1, its value gets set correctly and since L1 is a “variable”, that change would automatically be reflected back in goto L1. $\endgroup$ – Shashank Kumar Apr 15 '20 at 18:10
  • $\begingroup$ Consider the following code: "goto L1 ... L1:". What do you output for "goto L1"? $\endgroup$ – Yuval Filmus Apr 15 '20 at 18:11

Suppose you encounter a jump instruction "goto L1" before encountering the label L1 itself. The solution you propose (as far as I understand) is to reserve a location M1 in memory at which L1 will be stored, and to translate "goto L1" into an instruction of the form "jump to the address stored at address M1". Later on, upon reaching L1, you update location M1 with the address of L1.

This is a form of "runtime backpatching", in which the processor itself is doing the backpatching when running the code. Accessing memory tends to be slow, and so it is much better to hardcode addresses, shifting the effort from runtime to compile time. This is where backpatching comes in. When encountering "goto L1", the compiler will note that the address is missing, and will fill it in later, when the address of L1 is known.


Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.