daily pastebin goal
68%
SHARE
TWEET

pkmncompress.c

a guest Sep 24th, 2013 205 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. #include <stdlib.h>
  2. #include <stdio.h>
  3. #include <stdint.h>
  4. #include <string.h>
  5.  
  6. uint8_t *compressed;
  7. int xrows;
  8. int xwidth;
  9. int curbit;
  10. int curbyte;
  11.  
  12. void writebit(int bit)
  13. {
  14.         if(++curbit == 8)
  15.         {
  16.                 curbyte++;
  17.                 curbit = 0;
  18.         }
  19.         compressed[curbyte] |= bit << (7 - curbit);
  20. }
  21.  
  22. void method_1(uint8_t *RAM)
  23. {
  24.         int i;
  25.         int j;
  26.         int nibble_1;
  27.         int nibble_2;
  28.         int code_1;
  29.         int code_2;
  30.         int table;
  31.         static int method_1[2][0x10] = {{0x0, 0x1, 0x3, 0x2, 0x6, 0x7, 0x5, 0x4, 0xC, 0xD, 0xF, 0xE, 0xA, 0xB, 0x9, 0x8}, {0x8, 0x9, 0xB, 0xA, 0xE, 0xF, 0xD, 0xC, 0x4, 0x5, 0x7, 0x6, 0x2, 0x3, 0x1, 0x0}};
  32.  
  33.         for(i = 0; i < xrows * xwidth * 8; i++)
  34.         {
  35.                 j = i / xrows;
  36.                 j += i % xrows * xwidth * 8;
  37.                 if(!(i % xrows))
  38.                 {
  39.                         nibble_2 = 0;
  40.                 }
  41.                 nibble_1 = (RAM[j] >> 4) & 0x0F;
  42.                 table = 0;
  43.                 if(nibble_2 & 1)
  44.                 {
  45.                         table = 1;
  46.                 }
  47.                 code_1 = method_1[table][nibble_1];
  48.                 nibble_2 = RAM[j] & 0x0F;
  49.                 table = 0;
  50.                 if(nibble_1 & 1)
  51.                 {
  52.                         table = 1;
  53.                 }
  54.                 code_2 = method_1[table][nibble_2];
  55.                 RAM[j] = (code_1 << 4) | code_2;
  56.         }
  57. }
  58.  
  59. void RLE(int nums)
  60. {
  61.         int search;
  62.         int i;
  63.         int j;
  64.         int bitcount;
  65.         int number;
  66.         static unsigned int RLE[0x10] = {0x0001, 0x0003, 0x0007, 0x000F, 0x001F, 0x003F, 0x007F, 0x00FF, 0x01FF, 0x03FF, 0x07FF, 0x0FFF, 0x1FFF, 0x3FFF, 0x7FFF, 0xFFFF};
  67.  
  68.         bitcount = -1;
  69.         search = ++nums;
  70.         while(search > 0)
  71.         {
  72.                 for(i = 0; i < 0xF; i++)
  73.                 {
  74.                         if(RLE[i] == search)
  75.                         {
  76.                                 bitcount = i;
  77.                                 break;
  78.                         }
  79.                 }
  80.                 if(bitcount != -1)
  81.                 {
  82.                         break;
  83.                 }
  84.                 search--;
  85.         }
  86.         number = nums - RLE[bitcount];
  87.         for(j = 0; j < bitcount; j++)
  88.         {
  89.                 writebit(1);
  90.         }
  91.         writebit(0);
  92.         for(j = bitcount; j >= 0; j--)
  93.         {
  94.                 writebit((number >> j) & 1);
  95.         }
  96. }
  97.  
  98. void data_packet(uint8_t *bitgroups, int bgi)
  99. {
  100.         int i;
  101.         for(i = 0; i < bgi; i++)
  102.         {
  103.                 writebit((bitgroups[i] >> 1) & 1);
  104.                 writebit(bitgroups[i] & 1);
  105.         }
  106. }
  107.  
  108. int interpret_compress(uint8_t *RAM_1, uint8_t *RAM_2, int interpretation, int switchram)
  109. {
  110.         uint8_t *_1_RAM;
  111.         uint8_t *_2_RAM;
  112.         int i;
  113.         int ram;
  114.         int type;
  115.         int nums;
  116.         uint8_t *bitgroups;
  117.         int byte;
  118.         int bit;
  119.         int bitgroup;
  120.         int bgi = 0;
  121.  
  122.         _1_RAM = (uint8_t*) calloc(0x188, 1);
  123.         _2_RAM = (uint8_t*) calloc(0x188, 1);
  124.         if(switchram)
  125.         {
  126.                 memcpy(_1_RAM, RAM_2, 0x188);
  127.                 memcpy(_2_RAM, RAM_1, 0x188);
  128.         }
  129.         else
  130.         {
  131.                 memcpy(_1_RAM, RAM_1, 0x188);
  132.                 memcpy(_2_RAM, RAM_2, 0x188);
  133.         }
  134.  
  135.         switch(interpretation)
  136.         {
  137.                 case 1:
  138.                         method_1(_1_RAM);
  139.                         method_1(_2_RAM);
  140.                 break;
  141.                 case 2:
  142.                 case 3:
  143.                         for(i = 0; i < xrows * xwidth * 8; i++)
  144.                         {
  145.                                 _2_RAM[i] ^= _1_RAM[i];
  146.                         }
  147.                         method_1(_1_RAM);
  148.                 break;
  149.         }
  150.         if(interpretation == 3)
  151.         {
  152.                 method_1(_2_RAM);
  153.         }
  154.  
  155.         curbit = 7;
  156.         curbyte = 0;
  157.         compressed = (uint8_t*) calloc(0x310, 1);
  158.         compressed[0] = (xrows << 4) | xwidth;
  159.         writebit(switchram);
  160.  
  161.         for(ram = 0; ram < 2; ram++)
  162.         {
  163.                 type = 0;
  164.                 nums = 0;
  165.                 bitgroups = (uint8_t*) calloc(0x1000, 1);
  166.                 for(i = 0; i < xrows * xwidth * 32; i++)
  167.                 {
  168.                         byte = i / (xwidth * 32);
  169.                         byte = byte * xwidth * 8 + i % (xwidth * 8);
  170.                         bit = i / (xwidth * 8);
  171.                         bit = (bit * 2) % 8;
  172.                         if(ram)
  173.                         {
  174.                                 bitgroup = (_2_RAM[byte] >> (6 - bit)) & 3;
  175.                         }
  176.                         else
  177.                         {
  178.                                 bitgroup = (_1_RAM[byte] >> (6 - bit)) & 3;
  179.                         }
  180.                         if(!bitgroup)
  181.                         {
  182.                                 if(!type)
  183.                                 {
  184.                                         writebit(0);
  185.                                 }
  186.                                 else if(type == 1)
  187.                                 {
  188.                                         nums++;
  189.                                 }
  190.                                 else
  191.                                 {
  192.                                         data_packet(bitgroups, bgi);
  193.                                         writebit(0);
  194.                                         writebit(0);
  195.                                 }
  196.                                 type = 1;
  197.                                 free(bitgroups);
  198.                                 bitgroups = (uint8_t*) calloc(0x1000, 1);
  199.                                 bgi = 0;
  200.                         }
  201.                         else
  202.                         {
  203.                                 if(!type)
  204.                                 {
  205.                                         writebit(1);
  206.                                 }
  207.                                 else if(type == 1)
  208.                                 {
  209.                                         RLE(nums);
  210.                                 }
  211.                                 type = -1;
  212.                                 bitgroups[bgi++] = bitgroup;
  213.                                 nums = 0;
  214.                         }
  215.                 }
  216.                 if(type == 1)
  217.                 {
  218.                         RLE(nums);
  219.                 }
  220.                 else
  221.                 {
  222.                         data_packet(bitgroups, bgi);
  223.                 }
  224.                 if(!ram)
  225.                 {
  226.                         if(interpretation < 2)
  227.                         {
  228.                                 writebit(0);
  229.                         }
  230.                         else
  231.                         {
  232.                                 writebit(1);
  233.                                 writebit(interpretation - 2);
  234.                         }
  235.                 }
  236.         }
  237.         free(bitgroups);
  238.         free(_1_RAM);
  239.         free(_2_RAM);
  240.         return curbyte + 1;
  241. }
  242.  
  243. int compress(uint8_t *data, int width, int height)
  244. {
  245.         uint8_t *RAM_1;
  246.         uint8_t *RAM_2;
  247.         int i;
  248.         int newsize;
  249.         int size = -1;
  250.         uint8_t *current = NULL;
  251.  
  252.         xrows = height;
  253.         xwidth = width;
  254.  
  255.         RAM_1 = (uint8_t*) calloc(0x188, 1);
  256.         RAM_2 = (uint8_t*) calloc(0x188, 1);
  257.  
  258.         for(i = 0; i < xrows * xwidth * 8; i++)
  259.         {
  260.                 RAM_1[i] = data[(i << 1)];
  261.                 RAM_2[i] = data[(i << 1) | 1];
  262.         }
  263.  
  264.         for(i = 0; i < 6; i++)
  265.         {
  266.                 newsize = interpret_compress(RAM_1, RAM_2, i / 2 + 1, i % 2);
  267.                 if(size == -1 || newsize < size)
  268.                 {
  269.                         if(current != NULL)
  270.                         {
  271.                                 free(current);
  272.                         }
  273.                         current = (uint8_t*) calloc(0x310, 1);
  274.                         memcpy(current, compressed, newsize);
  275.                         free(compressed);
  276.                         size = newsize;
  277.                 }
  278.         }
  279.         compressed = (uint8_t*) calloc(0x310, 1);
  280.         memcpy(compressed, current, size);
  281.         free(current);
  282.  
  283.         free(RAM_1);
  284.         free(RAM_2);
  285.  
  286.         return size;
  287. }
  288.  
  289. int main(int argc, char *argv[])
  290. {
  291.         FILE *f;
  292.         int fz;
  293.         int size;
  294.         uint8_t *contents;
  295.         int tiles;
  296.  
  297.         if(argc < 3)
  298.         {
  299.                 printf("Usage: pkmncompress infile.2bpp outfile.bin\n");
  300.                 /*fputs("Usage: pkmncompress infile.2bpp outfile.bin\n", stderr);*/
  301.                 return EXIT_FAILURE;
  302.         }
  303.  
  304.         f = fopen(argv[1], "rb");
  305.  
  306.         if(!f)
  307.         {
  308.                 perror("Opening file failed");
  309.                 return EXIT_FAILURE;
  310.         }
  311.  
  312.         fseek(f, 0, SEEK_END);
  313.         fz = ftell(f);
  314.         if(fz == 0x310)
  315.         {
  316.                 tiles = 7;
  317.         }
  318.         else if(fz == 0x240)
  319.         {
  320.                 tiles = 6;
  321.         }
  322.         else if(fz == 0x190)
  323.         {
  324.                 tiles = 5;
  325.         }
  326.         else if(fz == 0x100)
  327.         {
  328.                 tiles = 4;
  329.         }
  330.         else
  331.         {
  332.                 printf("Error: wrong file size.\n");
  333.                 /*fputs("Error: wrong file size.\n", stderr);*/
  334.                 return EXIT_FAILURE;
  335.         }
  336.  
  337.         contents = (uint8_t*) calloc(0x310, 1);
  338.         fseek(f, 0, SEEK_SET);
  339.         fread(contents, 1, fz, f);
  340.         fclose(f);
  341.  
  342.         size = compress(contents, tiles, tiles);
  343.  
  344.         free(contents);
  345.  
  346.         f = fopen(argv[2], "wb");
  347.         fwrite(compressed, 1, size, f);
  348.  
  349.         free(compressed);
  350.  
  351.         printf("Success! File size: %i bytes\n", size);
  352.  
  353.         return EXIT_SUCCESS;
  354. }
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
 
Top