diff --git a/.gitignore b/.gitignore index d705156..56e5e11 100644 --- a/.gitignore +++ b/.gitignore @@ -53,6 +53,8 @@ builds/ Colleen Grace Sully +a.out Colleen_*.c Grace_*.c Sully_*.c +*test* diff --git a/3_Sully/Makefile b/3_Sully/Makefile index 8a3fd86..f317404 100644 --- a/3_Sully/Makefile +++ b/3_Sully/Makefile @@ -1,6 +1,6 @@ NAME = Sully SRCS = Sully.c CLONE = $(NAME)_kid.c -CREATE_CLONE = ./$(NAME) > $(CLONE) +CREATE_CLONE = ./$(NAME) include ../MakefileCommon diff --git a/3_Sully/Sully.c b/3_Sully/Sully.c index 89ac893..ac95bde 100644 --- a/3_Sully/Sully.c +++ b/3_Sully/Sully.c @@ -12,4 +12,3 @@ #define FFT(...) FT(__VA_ARGS__) FFT(PRINT) - diff --git a/3_Sully/calculate_print.sh b/3_Sully/calculate_print.sh new file mode 100755 index 0000000..93149c9 --- /dev/null +++ b/3_Sully/calculate_print.sh @@ -0,0 +1,16 @@ +#!/bin/bash + +# it's important to put the input_string inside single quotes +input_string='#include %[\r]#define PRINT %[\s]%[\r]#define FT(...) int main(){%[\\]%[\r]' + +special_cahracters=$(echo -E "$input_string" | grep -o "%\[..\]") +echo $special_cahracters + +# assiocative array : https://www.gnu.org/software/bash/manual/html_node/Arrays.html +declare -A instructions +instructions["%[\r]"]=10 +instructions["%[\s]"]="S" +instructions["%[\\]"]=92 +instructions["%[\"]"]=34 + +for key diff --git a/README.md b/README.md index 6ebdfc8..88c3bca 100644 --- a/README.md +++ b/README.md @@ -1 +1,163 @@ -# DR_QUINE +# DR QUINE + +#### constructing a quine with macro : +--- + +**a quine could be this structure basically :** +``` +int main() +{ + char *quine = THE_WHOLE_PROGRAM; + printf(quine); + return 0; +} +``` + +**in one line :** +``` +int main(){ char *quine = THIS_LINE_&_THE_LINES_AROUND; printf(quine); return 0; } +``` + +**whole code idea :** +``` +#include +#define MAIN() int main() { char *quine = "BEFORE" "THIS_MACRO_ITSELF" "AFTER"; printf(quine); return 0; } + +MAIN() +``` + + +#### let's try it +--- + +``` +#include +#define MAIN(s) int main() { char *quine = "#include \n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(s) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))\n"; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))"; + printf(quine); + return 0; +} +``` + +**problem :** the `char *quine` string should contain a copy of the whole code in place of "s" + + +#### second try +--- + +``` +#include +#define MAIN(s) int main() { char *quine = "#include \n#define MAIN(s) "s"\n\nMAIN(MAIN(s))\n"; printf(quine); return 0; } + +MAIN(MAIN(s)) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define MAIN(s) "int main() { char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))"; printf(quine); return 0; }"\n\nMAIN(MAIN(s))\n"; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = "#include \n#define MAIN(s) "int main() { char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))"; printf(quine); return 0; }"\n\nMAIN(MAIN(s))\n"; + printf(quine); + return 0; +} +``` + +**problem :** almost there, but the content of the string quine should be a litteral string instead of code + + + +#### lets stringify the content of the string quine +--- + +**the previous can be written with an extra step :** +``` +#define str(s) s +#define MAIN(s) content s content +MAIN(str(MAIN(s))) + +/* EQUIVALENT */ + +#define MAIN(s) content s content +MAIN((MAIN(s))) +``` + +**we can use this extra step to stringify the content :** +``` +#include +#define str(s) #s +#define MAIN(s) int main() { char *quine = "#include \n#define str(s) #s\n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(str(MAIN(s))) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define MAIN(s) ""MAIN(s)""\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; }` + + +**exploded view :** +``` +int main() +{ + char *quine = "#include \n#define MAIN(s) ""MAIN(s)""\n\nMAIN(str(MAIN(s)))"; + printf(quine); + return 0; +} +``` + +**problem :** oops, it stringified the paramter name, not it's expanded version, see https://gcc.gnu.org/onlinedocs/cpp/Stringizing.html + + +#### working stringification +--- + +``` +#include +#define xstr(s) #s +#define str(s) xstr(s) +#define MAIN(s) int main() { char *quine = "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(str(MAIN(s))) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) ""int main() { char *quine = \"#include \\n#define xstr(s) #s\\n#define str(s) xstr(s)\\n#define MAIN(s) \"s\"\\n\\nMAIN(str(MAIN(s)))\\n\"; printf(quine); return 0; }""\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = + "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) " + "int main() { char *quine = \"#include \\n#define xstr(s) #s\\n#define str(s) xstr(s)\\n#define MAIN(s) \"s\"\\n\\nMAIN(str(MAIN(s)))\\n\"; printf(quine); return 0; }" + "\n\nMAIN(str(MAIN(s)))\n"; + printf(quine); + return 0; +} +``` + +**output :** +``` +#include +#define xstr(s) #s +#define str(s) xstr(s) +#define MAIN(s) int main() { char *quine = "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(str(MAIN(s))) +``` + +**victory ;)** + diff --git a/notes.md b/notes.md index d7d0fe2..5e1829d 100644 --- a/notes.md +++ b/notes.md @@ -2,3 +2,327 @@ - [preprocessor strip comments before exapnding macros](https://stackoverflow.com/questions/1510869/does-the-c-preprocessor-strip-comments-or-expand-macros-first) - [create an include with a macro OR NOT](https://stackoverflow.com/questions/1135822/escaping-a-symbol-in-a-define-macro) +## Grace +--- + +#### 1 : a string containing itself, almost +--- + +``` +#define xstr(s) str(s) +#define str(s) char *quine = #s ; printf(quine); + +xstr(str()) +``` + +**expansions :** +-> `xstr ( char *quine = "" ; printf(quine); )` +-> `char *quine = "char *quine = \"\" ; printf(quine);" ; printf(quine);` + +**problem :** `\"\"` instead of `#s` : +-> `char *quine = "char *quine = #s ; printf(quine);" ; printf(quine);` + + +#### 1.2 : the output, first try +--- + +``` +#include +#define MAIN(s) int main(){ s return 0; } +#define xstr(s) str(s) +#define str(s) char *quine = #s ; printf(quine); + +MAIN(xstr(str())) +``` + +**expansions :** +-> `MAIN( xstr( char *quine = "" ; printf(quine); ))` +-> `MAIN( char *quine = "char *quine = \"\" ; printf(quine);" ; printf(quine); )` +-> `int main(){ char *quine = "char *quine = \"\" ; printf(quine);" ; printf(quine); return 0; }` + +**exploded view :** +``` +int main(){ + char *quine = "char *quine = \"\" ; printf(quine);" ; + printf(quine); + return 0; +} +``` + +**output :** +``` +char *quine = "" ; printf(quine); +``` + +**problem 1 :** missing the main function around the content +**problem 2 :** quine does not contain itself, but an empty string + + +#### 1.3 : the output, second try +--- + +``` +#include +#define MAIN(s) int main(){ s return 0; } +#define xstr(s) str(s) +#define str(s) char *quine = #s ; printf(quine); + +MAIN(xstr(MAIN(xstr(str())))) +``` + +**expansions :** +-> `MAIN( xstr( MAIN( xstr( char *quine = "" ; printf(quine); ))))` +-> `MAIN( xstr( MAIN( char *quine = "char *quine = \"\" ; printf(quine);" ; printf(quine); )))` +-> `MAIN( xstr( int main(){ char *quine = "char *quine = \"\" ; printf(quine);" ; printf(quine); return 0; } ))` +-> `MAIN( char *quine = "int main(){ char *quine = \"char *quine = \\\"\\\" ; printf(quine);\" ; printf(quine); return 0; }" ; printf(quine); )` +-> `int main(){ char *quine = "int main(){ char *quine = \"char *quine = \\\"\\\" ; printf(quine);\" ; printf(quine); return 0; }" ; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = + " + int main() + { + char *quine = \"char *quine = \\\"\\\" ; printf(quine);\" ; + printf(quine); + return 0; + } + "; + + printf(quine); + return 0; +} +``` + +**output :** +``` +int main(){ char *quine = "char *quine = \"\" ; printf(quine);" ; printf(quine); return 0; }% +``` + +**exploded view :** +``` +int main() +{ + char *quine = "char *quine = \"\" ; printf(quine);"; + printf(quine); + return 0; +} +``` + +**problem :** this new program will only print : +`char *quine = "" ; printf(quine);` + + + +#### 1.3 : the output, third try +--- + +``` +#include +#define MAIN(s) int main(){ s return 0; } +#define xstr(s) str(s) +#define str(s) char *quine = #s ; printf(quine); + +MAIN(xstr(MAIN(xstr(MAIN(xstr()))))) +``` +**output :** +`int main(){ char *quine = "int main(){ char *quine = \"\" ; printf(quine); return 0; }" ; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = + " + int main() + { + char *quine = \"\"; + printf(quine); + return 0; + } + "; + printf(quine); + return 0; +} +``` + +**problem :** we cannot gon on like this, there will always be one level missing +**idea :** changing the inner `char* quine =` content to '%s' and printing `printf(quine, quine)` + + + + +#### 2 : second approach +--- + +**a quine could be this structure basically :** +``` +int main() +{ + char *quine = THE_WHOLE_PROGRAM; + printf(quine); + return 0; +} +``` + +**in one line :** +``` +int main(){ char *quine = THIS_LINE_&_THE_LINES_AROUND; printf(quine); return 0; } +``` + +**whole code idea :** +``` +#include +#define MAIN() int main() { char *quine = "BEFORE" "THIS_MACRO_ITSELF" "AFTER"; printf(quine); return 0; } + +MAIN() +``` + + +#### 2.1 : let's try it +--- + +``` +#include +#define MAIN(s) int main() { char *quine = "#include \n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(s) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))\n"; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))"; + printf(quine); + return 0; +} +``` + +**problem :** the `char *quine` string should contain a copy of the whole code in place of "s" + + +#### 2.2 : second try +--- + +``` +#include +#define MAIN(s) int main() { char *quine = "#include \n#define MAIN(s) "s"\n\nMAIN(MAIN(s))\n"; printf(quine); return 0; } + +MAIN(MAIN(s)) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define MAIN(s) "int main() { char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))"; printf(quine); return 0; }"\n\nMAIN(MAIN(s))\n"; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = "#include \n#define MAIN(s) "int main() { char *quine = "#include \n#define MAIN(s) "s "\n\nMAIN(MAIN(s))"; printf(quine); return 0; }"\n\nMAIN(MAIN(s))\n"; + printf(quine); + return 0; +} +``` + +**problem :** almost there, but the content of the string quine should be a litteral string instead of code + + + +#### 2.3 : lets stringify the content of the string quine +--- + +**the previous can be written with an extra step :** +``` +#define str(s) s +#define MAIN(s) content s content +MAIN(str(MAIN(s))) + +/* EQUIVALENT */ + +#define MAIN(s) content s content +MAIN((MAIN(s))) +``` + +**we can use this extra step to stringify the content :** +``` +#include +#define str(s) #s +#define MAIN(s) int main() { char *quine = "#include \n#define str(s) #s\n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(str(MAIN(s))) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define MAIN(s) ""MAIN(s)""\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; }` + + +**exploded view :** +``` +int main() +{ + char *quine = "#include \n#define MAIN(s) ""MAIN(s)""\n\nMAIN(str(MAIN(s)))"; + printf(quine); + return 0; +} +``` + +**problem :** oops, it stringified the paramter name, not it's expanded version, see https://gcc.gnu.org/onlinedocs/cpp/Stringizing.html + + +#### 2.4 : working stringification +--- + +``` +#include +#define xstr(s) #s +#define str(s) xstr(s) +#define MAIN(s) int main() { char *quine = "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(str(MAIN(s))) +``` + +**expansions :** +-> `int main() { char *quine = "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) ""int main() { char *quine = \"#include \\n#define xstr(s) #s\\n#define str(s) xstr(s)\\n#define MAIN(s) \"s\"\\n\\nMAIN(str(MAIN(s)))\\n\"; printf(quine); return 0; }""\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; }` + +**exploded view :** +``` +int main() +{ + char *quine = + "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) " + "int main() { char *quine = \"#include \\n#define xstr(s) #s\\n#define str(s) xstr(s)\\n#define MAIN(s) \"s\"\\n\\nMAIN(str(MAIN(s)))\\n\"; printf(quine); return 0; }" + "\n\nMAIN(str(MAIN(s)))\n"; + printf(quine); + return 0; +} +``` + +**output :** +``` +#include +#define xstr(s) #s +#define str(s) xstr(s) +#define MAIN(s) int main() { char *quine = "#include \n#define xstr(s) #s\n#define str(s) xstr(s)\n#define MAIN(s) "s"\n\nMAIN(str(MAIN(s)))\n"; printf(quine); return 0; } + +MAIN(str(MAIN(s))) +``` + +**victory ;)** + + + + + + + + + + + +