aaaaaa123456789 icon

C quine

aaaaaa123456789 | PRO | 12/18/20 11:09:01 AM UTC (Edited) | 0 ⭐ | 462 👁️ | Never ⏰ | []
C |

10.2 KB

|

None

|

0 👍

/

0 👎

const char * sourceCode =
  "I2luY2x1ZGUgPHN0ZGlvLmg+CiNpbmNsdWRlIDxzdGRsaWIuaD4KI2luY2x1ZGUg"
  "PHN0cmluZy5oPgoKLyoKICAgVGhpcyBwcm9ncmFtIGlzIGEgcXVpbmUuIFRoYXQg"
  "bWVhbnMsIGl0IG91dHB1dHMgaXRzIG93biBzb3VyY2Ugd2hlbiBydW4uCiAgIFRo"
  "ZSBnbG9iYWwgdmFyaWFibGUgc291cmNlQ29kZSBzaW1wbHkgY29udGFpbnMgYSBi"
  "YXNlNjQgZW5jb2Rpbmcgb2YKICAgZXZlcnl0aGluZyB0aGF0IGZvbGxvd3MgLS0g"
  "dGhlIGNvZGUgb25seSBoYXMgdG8gcHJpbnQgaXQgYXMgZGF0YSwgYW5kIHRoZW4K"
  "ICAgYXMgY29kZS4gSWRlYSB0YWtlbiBmcm9tIGh0dHA6Ly93d3cubWFkb3JlLm9y"
  "Zy9+ZGF2aWQvY29tcHV0ZXJzL3F1aW5lLmh0bWwKICAgKG5vdCBzdG9sZW4sIGJ1"
  "dCB0aGUgc2FtZSBwcmluY2lwbGUgaXMgYXBwbGllZCkuCiAgIFRoaXMgc2hvdWxk"
  "IGNvbXBpbGUgdW5kZXIgYW55IEM5OS1jb21wbGlhbnQgY29tcGlsZXIsIGFuZCBp"
  "dCdzIG5vdCBsaW1pdGVkCiAgIHRvIGFueSBzcGVjaWZpYyBhcmNoaXRlY3R1cmUu"
  "CiAgIFRoZSBiYXNlNjQgZW5jb2RpbmcgdXNlcyArIGFuZCAvIGFzIDYyIGFuZCA2"
  "MywgYW5kIG9taXRzIHRyYWlsaW5nIGVxdWFscy4KICAgCiAgIElmIHlvdSByZWFk"
  "IHRoaXMgeW91J3JlIGEgbm9vYi4KKi8KCnZvaWQgb3V0cHV0RGF0YShjb25zdCBj"
  "aGFyICopOwpjaGFyICogYmFzZTY0X2RlY29kZShjb25zdCBjaGFyICopOwp1bnNp"
  "Z25lZCBjaGFyIGJhc2U2NF9pbmRleChjaGFyKTsKCmlubGluZSB2b2lkIG91dHB1"
  "dCAoY29uc3QgY2hhciAqIHN0cmluZykgewogIC8vIGxldCdzIHNwYXJlIG1lIHNv"
  "bWUgdHlwaW5nCiAgcHJpbnRmKCIlcyIsIHN0cmluZyk7Cn0KCmludCBtYWluICh2"
  "b2lkKSB7CiAgb3V0cHV0KCJjb25zdCBjaGFyICogc291cmNlQ29kZSA9XG4iKTsg"
  "Ly8gZmlyc3Qgb2YgYWxsLCB0aGUgZGVjbGFyYXRpb24uLi4KICBvdXRwdXREYXRh"
  "KHNvdXJjZUNvZGUpOyAvLyAuLi5hbmQgdGhlbiB0aGUgZGF0YSBpdCBjb250YWlu"
  "cwogIGNoYXIgKiBwYXJzZWRDb2RlID0gYmFzZTY0X2RlY29kZShzb3VyY2VDb2Rl"
  "KTsgLy8gZGVjb2RlIHRoZSBkYXRhCiAgb3V0cHV0KHBhcnNlZENvZGUpOyAgLy8g"
  "YW5kIG91dHB1dCB0aGUgY29kZSAoaW4gdGhlIGRlY29kZWQgZGF0YSkKICBmcmVl"
  "KHBhcnNlZENvZGUpOyAvLyByZWxlYXNlIHRoZSBidWZmZXIgdGhhdCBiYXNlNjRf"
  "ZGVjb2RlKCkgYWNxdWlyZWQKICByZXR1cm4gMDsKfQoKdm9pZCBvdXRwdXREYXRh"
  "IChjb25zdCBjaGFyICogc3RyaW5nKSB7CiAgLy8gNjQgY2hhcmFjdGVycyBwZXIg"
  "bGluZSwgb3RoZXIgdGhhbiB0aGUgbGFzdCBsaW5lCiAgLy8gbGFzdCBsaW5lIGhh"
  "cyB0aGUgc2VtaWNvbG9uCiAgY2hhciBidWZmZXJbNjVdOwogIGJ1ZmZlcls2NF0g"
  "PSAwOyAvLyBtYWtlIHN1cmUgdGhlIG51bGwgdGVybWluYXRvciBpcyBhbHJlYWR5"
  "IHRoZXJlCiAgY29uc3QgY2hhciAqIGN1cnJlbnQ7CiAgdW5zaWduZWQgcmVtYWlu"
  "ZGVyID0gc3RybGVuKHN0cmluZyk7CiAgZm9yIChjdXJyZW50ID0gc3RyaW5nOyBy"
  "ZW1haW5kZXIgPj0gNjQ7IGN1cnJlbnQgKz0gNjQsIHJlbWFpbmRlciAtPSA2NCkg"
  "ewogICAgLy8gaXRlcmF0ZSBmb3IgZXZlcnkgNjQgY2hhcmFjdGVycyBvZiB0aGUg"
  "c3RyaW5nLCB1bnRpbCBub3QgZW5vdWdoIHJlbWFpbgogICAgb3V0cHV0KCIgIFwi"
  "Iik7IC8vIGV2ZXJ5IGxpbmUgc3RhcnRzIGxpa2UgdGhpcwogICAgbWVtY3B5KGJ1"
  "ZmZlciwgY3VycmVudCwgNjQpOyAvLyB0aGUgY3VycmVudCA2NCBjaGFyYWN0ZXJz"
  "CiAgICBvdXRwdXQoYnVmZmVyKTsKICAgIG91dHB1dCgiXCJcbiIpOyAvLyBhbmQg"
  "ZXZlcnkgbGluZSBlbmRzIGxpa2UgdGhpcwogIH0KICBvdXRwdXQoIiAgXCIiKTsg"
  "Ly8gdGhlIGZpbmFsIGxpbmUgb2YgdGhlIGRhdGEgZGVjbGFyYXRpb24KICBtZW1j"
  "cHkoYnVmZmVyLCBjdXJyZW50LCByZW1haW5kZXIpOwogIGJ1ZmZlcltyZW1haW5k"
  "ZXJdID0gMDsgLy8gbWFrZSBzdXJlIHRoZSB0ZXJtaW5hdG9yIGlzIGluIHRoZSBy"
  "aWdodCBwbGFjZSEKICBvdXRwdXQoYnVmZmVyKTsKICBvdXRwdXQoIlwiO1xuXG4i"
  "KTsgLy8gbGFzdCBsaW5lIGhhcyBhIHNlbWljb2xvbiwgYW5kIHR3byBuZXdsaW5l"
  "cwp9CgpjaGFyICogYmFzZTY0X2RlY29kZSAoY29uc3QgY2hhciAqIGRhdGEpIHsK"
  "ICAvLyB0aGlzIGp1c3QgZGVjb2RlcyB0aGUgYmFzZTY0IGVuY29kZWQgZGF0YSBh"
  "bmQgcmV0dXJucyB0aGUgcmVzdWx0CiAgY2hhciAqIHJlc3VsdCA9IG1hbGxvYyhz"
  "dHJsZW4oZGF0YSkgKyAxKTsgLy8gdGhpcyB3aWxsIGNlcnRhaW5seSBzdWZmaWNl"
  "CiAgdW5zaWduZWQgcmVtYWluaW5nID0gc3RybGVuKGRhdGEpOwogIGNvbnN0IGNo"
  "YXIgKiBjdXJyZW50OyAvLyBjdXJyZW50IHBvaW50ZXIgdG8gdGhlIHNvdXJjZSBi"
  "dWZmZXIKICBjaGFyICogaW5zZXJ0aW9uOyAvLyBpbnNlcnRpb24gcG9pbnRlciB0"
  "byB0aGUgZGVzdGluYXRpb24gYnVmZmVyCiAgdW5zaWduZWQgY2hhciBkZWNvZGlu"
  "Z3NbNF07IC8vIHRlbXBvcmFyeSBidWZmZXIKICB1bnNpZ25lZCBjaGFyIGk7CiAg"
  "Zm9yIChjdXJyZW50ID0gZGF0YSwgaW5zZXJ0aW9uID0gcmVzdWx0OyAvLyBpbml0"
  "aWFsIHZhbHVlcwogICAgICAgcmVtYWluaW5nID49IDQ7IC8vIGl0ZXJhdGUgd2hp"
  "bGUgdGhlcmUncyBhdCBsZWFzdCA0IGJ5dGVzIHRvIGRlY29kZQogICAgICAgY3Vy"
  "cmVudCArPSA0LCBpbnNlcnRpb24gKz0gMywgcmVtYWluaW5nIC09IDQpIHsgLy8g"
  "aW5jcmVtZW50IGFuZCBzdWNoCiAgICBmb3IgKGkgPSAwOyBpIDwgNDsgaSArKykg"
  "ZGVjb2RpbmdzW2ldID0gYmFzZTY0X2luZGV4KGN1cnJlbnRbaV0pOwogICAgLy8g"
  "YW5kIG5vdyBkZWNvZGUgdGhlIGJhc2U2NCBkYXRhLiBUaGlzIGNvZGUgaXMgYXdm"
  "dWwsIEkga25vdwogICAgaW5zZXJ0aW9uWzBdID0gKGRlY29kaW5nc1swXSA8PCAy"
  "KSB8IChkZWNvZGluZ3NbMV0gPj4gNCk7CiAgICBpbnNlcnRpb25bMV0gPSAoKGRl"
  "Y29kaW5nc1sxXSAmIDE1KSA8PCA0KSB8IChkZWNvZGluZ3NbMl0gPj4gMik7CiAg"
  "ICBpbnNlcnRpb25bMl0gPSAoKGRlY29kaW5nc1syXSAmIDMpIDw8IDYpIHwgZGVj"
  "b2RpbmdzWzNdOwogIH0KICBpZiAocmVtYWluaW5nKSAvLyBpZiBzb21ldGhpbmcg"
  "cmVtYWlucywgZGVjb2RlIGl0IHRvbwogICAgZm9yIChpID0gMDsgaSA8IHJlbWFp"
  "bmluZzsgaSArKykgZGVjb2RpbmdzW2ldID0gYmFzZTY0X2luZGV4KGN1cnJlbnRb"
  "aV0pOwogIHN3aXRjaCAocmVtYWluaW5nKSB7CiAgICBjYXNlIDM6CiAgICAgIGlu"
  "c2VydGlvblsxXSA9ICgoZGVjb2RpbmdzWzFdICYgMTUpIDw8IDQpIHwgKGRlY29k"
  "aW5nc1syXSA+PiAyKTsKICAgICAgLy8gbm8gYnJlYWsgb24gcHVycG9zZSEKICAg"
  "IGNhc2UgMjoKICAgICAgaW5zZXJ0aW9uWzBdID0gKGRlY29kaW5nc1swXSA8PCAy"
  "KSB8IChkZWNvZGluZ3NbMV0gPj4gNCk7CiAgfQogIGluc2VydGlvbiArPSByZW1h"
  "aW5pbmcgPyByZW1haW5pbmcgOiAxOyAvLyB1Z2x5LCBidXQgd29ya3MKICBpbnNl"
  "cnRpb25bLTFdID0gMDsgLy8gYmVmb3JlIHRoZSB3dGYsIHRoaXMganVzdCBhZGRz"
  "IGEgbnVsbCB0ZXJtaW5hdG9yCiAgcmV0dXJuIHJlYWxsb2MocmVzdWx0LCBpbnNl"
  "cnRpb24gLSByZXN1bHQpOyAvLyBva2F5LCB5b3UgY2FuIHd0ZiBub3cKfQoKdW5z"
  "aWduZWQgY2hhciBiYXNlNjRfaW5kZXggKGNoYXIgY2hhcmFjdGVyKSB7CiAgLy8g"
  "dGhpcyBmdW5jdGlvbiByZXR1cm5zIGEgbnVtYmVyIGZyb20gMCB0byA2MyBpbmRp"
  "Y2F0aW5nIHdoYXQgdGhlIHZhbHVlCiAgLy8gb2YgYSBjZXJ0YWluIGJhc2U2NCBl"
  "bmNvZGluZyBjaGFyYWN0ZXIgaXMKICAvLyBBLVo6IDAtMjUsIGEtejogMjYtNTEs"
  "IDAtOTogNTItNjEsICs6IDYyLCAvOiA2MwogIGlmIChjaGFyYWN0ZXIgPT0gJysn"
  "KSByZXR1cm4gNjI7CiAgaWYgKGNoYXJhY3RlciA9PSAnLycpIHJldHVybiA2MzsK"
  "ICBpZiAoKGNoYXJhY3RlciA+PSAnMCcpICYmIChjaGFyYWN0ZXIgPD0gJzknKSkg"
  "cmV0dXJuIGNoYXJhY3RlciArIDUyIC0gJzAnOwogIGlmICgoY2hhcmFjdGVyID49"
  "ICdBJykgJiYgKGNoYXJhY3RlciA8PSAnWicpKSByZXR1cm4gY2hhcmFjdGVyIC0g"
  "J0EnOwogIGlmICgoY2hhcmFjdGVyID49ICdhJykgJiYgKGNoYXJhY3RlciA8PSAn"
  "eicpKSByZXR1cm4gY2hhcmFjdGVyICsgMjYgLSAnYSc7CiAgcmV0dXJuIDI1NTsg"
  "Ly8gaW52YWxpZCB2YWx1ZQp9Cg";
 
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
 
/*
   This program is a quine. That means, it outputs its own source when run.
   The global variable sourceCode simply contains a base64 encoding of
   everything that follows -- the code only has to print it as data, and then
   as code. Idea taken from http://www.madore.org/~david/computers/quine.html
   (not stolen, but the same principle is applied).
   This should compile under any C99-compliant compiler, and it's not limited
   to any specific architecture.
   The base64 encoding uses + and / as 62 and 63, and omits trailing equals.
   
   If you read this you're a noob.
*/
 
void outputData(const char *);
char * base64_decode(const char *);
unsigned char base64_index(char);
 
inline void output (const char * string) {
  // let's spare me some typing
  printf("%s", string);
}
 
int main (void) {
  output("const char * sourceCode =\n"); // first of all, the declaration...
  outputData(sourceCode); // ...and then the data it contains
  char * parsedCode = base64_decode(sourceCode); // decode the data
  output(parsedCode);  // and output the code (in the decoded data)
  free(parsedCode); // release the buffer that base64_decode() acquired
  return 0;
}
 
void outputData (const char * string) {
  // 64 characters per line, other than the last line
  // last line has the semicolon
  char buffer[65];
  buffer[64] = 0; // make sure the null terminator is already there
  const char * current;
  unsigned remainder = strlen(string);
  for (current = string; remainder >= 64; current += 64, remainder -= 64) {
    // iterate for every 64 characters of the string, until not enough remain
    output("  \""); // every line starts like this
    memcpy(buffer, current, 64); // the current 64 characters
    output(buffer);
    output("\"\n"); // and every line ends like this
  }
  output("  \""); // the final line of the data declaration
  memcpy(buffer, current, remainder);
  buffer[remainder] = 0; // make sure the terminator is in the right place!
  output(buffer);
  output("\";\n\n"); // last line has a semicolon, and two newlines
}
 
char * base64_decode (const char * data) {
  // this just decodes the base64 encoded data and returns the result
  char * result = malloc(strlen(data) + 1); // this will certainly suffice
  unsigned remaining = strlen(data);
  const char * current; // current pointer to the source buffer
  char * insertion; // insertion pointer to the destination buffer
  unsigned char decodings[4]; // temporary buffer
  unsigned char i;
  for (current = data, insertion = result; // initial values
       remaining >= 4; // iterate while there's at least 4 bytes to decode
       current += 4, insertion += 3, remaining -= 4) { // increment and such
    for (i = 0; i < 4; i ++) decodings[i] = base64_index(current[i]);
    // and now decode the base64 data. This code is awful, I know
    insertion[0] = (decodings[0] << 2) | (decodings[1] >> 4);
    insertion[1] = ((decodings[1] & 15) << 4) | (decodings[2] >> 2);
    insertion[2] = ((decodings[2] & 3) << 6) | decodings[3];
  }
  if (remaining) // if something remains, decode it too
    for (i = 0; i < remaining; i ++) decodings[i] = base64_index(current[i]);
  switch (remaining) {
    case 3:
      insertion[1] = ((decodings[1] & 15) << 4) | (decodings[2] >> 2);
      // no break on purpose!
    case 2:
      insertion[0] = (decodings[0] << 2) | (decodings[1] >> 4);
  }
  insertion += remaining ? remaining : 1; // ugly, but works
  insertion[-1] = 0; // before the wtf, this just adds a null terminator
  return realloc(result, insertion - result); // okay, you can wtf now
}
 
unsigned char base64_index (char character) {
  // this function returns a number from 0 to 63 indicating what the value
  // of a certain base64 encoding character is
  // A-Z: 0-25, a-z: 26-51, 0-9: 52-61, +: 62, /: 63
  if (character == '+') return 62;
  if (character == '/') return 63;
  if ((character >= '0') && (character <= '9')) return character + 52 - '0';
  if ((character >= 'A') && (character <= 'Z')) return character - 'A';
  if ((character >= 'a') && (character <= 'z')) return character + 26 - 'a';
  return 255; // invalid value
}

Comments