I'm new to coding in c. I want to decode RLE encoded binary files (vintage, rare pic format) with these conditions:
character, followed by number of characters
run count is valid for counts >=4
0 is encoded 00 00
1 is encoded 00 01
10 (hex ?) is LF
EOF is encoded as 00 03
bottom byte (after EOF is 0A)
there's a 2 byte count: , 4<=<=127 , >8> ! 128, &255, examples
0 1 2 3 4 5 encodes as 0 0 1 2 3 4 5 encode 0 as 0,0
5 6 7 8 9 10 encodes as 5 6 7 8 9 0 1 encode 10 as 0,1
5...(200 times) encodes as 5 0 128 200 long repeat count of 200
7...(515 times) encodes as 7 0 130 3 long repeat count of 16_203
The file format is complicated and includes:
variable header length (512/1024 bytes) different compressions, including different RLE compressions (horizontal, vertical) variable color maps (variable lengths) and none, stereo pics, CAD pics, fractals, geosat pics, etc, but for now I just want to decode headerless data.
I searched a lot for RLE here and elsewhere and tried for some days but there are mainly threads about strings and none about selected conditions like for character 0 etc. And especially for checking 3 Bytes.
I have documents and codes in 2 older languages including Assembler. I found here a similar code in c++ but I couldn't translate it properly. I managed to make some c programs without compiling errors, but the result is wrong.
The best code is below. It reads multiple bytes but missing some "00" bytes. Bytes 1+3 are correct. Byte 2 is 0, Byte 4 missing.
The output to file is completely wrong and just 3 bytes. Even the 1st byte is wrong. (80)
I'm confused reading 3 bytes with 2 variables. Byte flipping?
Can anybody help? Thanks!
while (!feof(fp1))
{ //originally also have to check if 1st char=10 (LF) and overrides that
if(fread(buf,1,2,fp1)!=2) //Read two bytes: original code was number of characters + characters
// but I have characters + number of ch, and more conditions
continue; // was break;
ch = buf[0]; //was num ch instead of ch, also swapped below at buf 1
printf("%x\n", ch); //later added this to output to screen, reads more than output but bytes like 0 missing
if(ch==0) {
if(ch==1) {
ch=10; // code for LF
continue; // is this correct? continue or return (0) or -1? same below
}else{
if(ch==0) {
ch=0; // 00 00 encoded as 0
continue;
}else{
if(ch==3); //EOF, after that bottom byte 0A follows
return (0);
}
} //else beep? return -1, break, but I rely on proper image not having 00 04...
}
}
num = buf[1];
char * chbuf = (char *)malloc(num);
//main code from_WRITE IMAGE, although read
if(num==1) { // no action v----------v-----------v-------
} else if (num<4) { // run counts only when count =>4
for (int i =0;i < num;i++)
chbuf[i] = ch;
fwrite(&chbuf,1,num,fp2); //num ? ,1? or 0 was fwrite(chbuf
}else if (num<=127); {
for (int i =0;i < num;i++)
chbuf[i] = num; ////newest added is this right?
if (num==10) {
fwrite(&chbuf,1,num,fp2); //num--; //num ?, or is it ch or char or i?
}else {
if ((ch&255)==10) { // was num&, I tried all, num and ch , always wrong
num++;
fwrite(&chbuf,1,ch,fp2); // was num--; at end
num++; // is num++ right? but neverless always just 3 bytes
fwrite(&chbuf,2,((unsigned) num>>8|0x80),fp2); // was chbuf 1, also checked unsigned char, 80, else
num++;
fwrite(&chbuf,1,ch,fp2); // was 1
}
}
}
free(chbuf);
New code 3
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
//3rd code this time with internal string, code 2 worked (read 2 bytes from file, print to screen)
int i, j; //output should be 88 times 05, 4 times 06
int main()
{
char string[] = "0500580604"; //hex test input to not have external file
//for now no check for conditions like EOF, 00 at begin
int number1 = atoi(string [0]); //convert string to byte was [1]
int number2 = atoi(string [1]);
int number3 = atoi(string [2]);
if (number2 == 0){ //read byte 2 and check if it's a count, Byte 1 is a char
if (number2 >=4){ //check byte 2 if valid count or char
}else {printf("%x\n", number1, number2); //byte 2 is a char
} return (0);
if (number3<127){ //check byte 3 if its a long run
for (int i =0;i < number2;i++) // print byte2 times the char
printf("%x\n", number1);
}else {
for (int i =0;i <number3;i++) //print byte3 times the char
printf("%x\n", number1);
return (0);
}
}
}