Code:
#include <stdio.h>
#include <stdlib.h>
#include <malloc.h>
#include <assert.h>
#define INPUTFILENAME "input.rle"
#define OUTPUTFILENAME "output.rle"
#define TEMPFILENAME "rle.tmp"
FILE *f;
long fsize;
/////////////////////////////////
// Return file size in bytes //
/////////////////////////////////
long filesize(FILE *f)
{
long pos, fsize;
pos = ftell(f);
fseek(f, 0L, SEEK_END);
fsize = ftell(f);
fseek(f, pos, SEEK_SET);
return fsize;
}
/////////////////////////////////////////////////////////
// Read input file to memory to speed up compression //
/////////////////////////////////////////////////////////
char *rle_readinputstream(char *inputstream)
{
char *stream;
f = fopen(inputstream,"r+b");
assert(f != NULL);
fsize = filesize(f);
stream = (char *)calloc(fsize, sizeof(char));
assert(stream != NULL);
fread(stream, fsize, 1, f);
fclose(f);
return stream;
}
///////////////////////////////////////////////////////
// Encode input stream and write it to output file //
///////////////////////////////////////////////////////
void rle_encode(char *stream)
{
int k;
char byte, freq;
f = fopen(TEMPFILENAME,"w+b");
assert(f != NULL);
k = 0;
while (k < fsize) {
byte = stream[k];
freq = 0;
while (stream[k++] == byte && freq < 63) freq++;
--k;
if (freq == 1 && byte < 0xC0)
fwrite(&byte, sizeof(byte), 1, f);
else {
freq |= 0xC0;
fwrite(&freq, sizeof(char), 1, f);
fwrite(&byte, sizeof(char), 1, f);
}
}
fclose(f);
}
///////////////////////////////////////////////////////
// Decode input stream and write it to output file //
///////////////////////////////////////////////////////
void rle_decode(char *stream)
{
int k, l;
char byte, freq;
f = fopen(OUTPUTFILENAME,"w+b");
assert(f != NULL);
k = 0;
while (k < fsize) {
byte = stream[k++];
if ((byte & 0xC0) == 0xC0) {
freq = byte & 0x3F;
byte = stream[k++];
}
else freq = 1;
for (l = 0; l < freq; l++)
fwrite(&byte, sizeof(byte), 1, f);
}
fclose(f);
}
////////////////////
// Main program //
////////////////////
void main()
{
char *stream;
printf("RLE compression\n");
printf("Copyright (c) 1997 by Matjaz Trtnik\n");
stream = rle_readinputstream(INPUTFILENAME);
rle_encode(stream);
stream = rle_readinputstream(TEMPFILENAME);
rle_decode(stream);
}
This code does runlength coding ...but as it uses 2 MSB's as indicator of counter it can only code .txt files...what should i do if Iwant to do it for any other type of data as well.
Thanks,
Edesign