program that prints itself, how does it work?

SpeedBirdNine picture SpeedBirdNine · Oct 7, 2011 · Viewed 18.6k times · Source

I came across a program that prints itself on this site, i.e. it prints the program code.

The program code is:

#include <stdio.h>
char *program = "#include <stdio.h>%cchar *program = %c%s%c;%cint main()%c{%cprintf(program, 10, 34, program, 34, 10, 10, 10, 10, 10, 10);%c    return 0;%c}%c";
//what is this line doing, what is the use of %c and %s and what properties of %c and %s are being used here?
int main()
{
        printf(program, 10, 34, program, 34, 10, 10, 10, 10, 10, 10);
        //what is this print function doing, and how?
        return 0;
}

And the explanation given is:

The two key tricks here are using a string with an embedded %s specifier to allow the string to contain itself when printed, and to use the %c format specifier to allow printing out special characters like newlines, which could not otherwise be embedded in the output string.

I didn't understand how the program is working. I have mentioned the lines i need the explanation about, how they work and what are they doing. Please explain.

Answer

ammar26 picture ammar26 · Oct 7, 2011
char *program = "#include <stdio.h>%cchar *program = %c%s%c;%cint main()%c{%cprintf(program, 10, 34, program, 34, 10, 10, 10, 10, 10, 10);%c    return 0;%c}%c";

There is a char pointer name "program" which is used to store the string and %c and %s are format specifiers for char and string arguments respectively.

printf(program, 10, 34, program, 34, 10, 10, 10, 10, 10, 10);

printf function is printing output to console, 10 here is ASCII code for NEWLINE and 34 for " printf parameters are doing

  • program , passing string to be printed
  • 10 , passing 10 ASCII code for first %c (will be converted to character newline)
  • program , passing same string again to %s in program to print same string again
  • 34 , passing 34 ASCII code for second %c (will be converted to character double qoutes)
  • 10 , passing 10 ASCII code for 3rd %c (will be converted to character newline)
  • 10 , passing 10 ASCII code for 4th %c (will be converted to character newline)
  • 10 , passing 10 ASCII code for 5th %c (will be converted to character newline)
  • 10 , passing 10 ASCII code for 6th %c (will be converted to character newline)
  • 10 , passing 10 ASCII code for 7th %c (will be converted to character newline)
  • 10 , passing 10 ASCII code for 8th %c (will be converted to character newline)