-
Notifications
You must be signed in to change notification settings - Fork 0
/
save_bits.h
224 lines (183 loc) · 3.87 KB
/
save_bits.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
/*
* TRABALHO 03
* Grupo 04:
* Vanessa Apolinário de Lima
* Caio Augusto da Silva Gomes
* Fernando Cury Gorodscy
*
* Gravação de Bits
*/
#ifndef _SAVE_BITS_h
#define _SAVE_BITS_h
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#define TAKE_N_BITS_FROM(b, p, n) ((b) >> (p)) & ((1 << (n)) - 1)
int nbits_freq(int nbits, int freq) {
int result = 0;
nbits = nbits == 32 ? 0 : nbits;
if (freq > 64 || nbits > 31) {
printf("Tamanho de frequência inválida\n");
return 0;
}
freq = freq-1; /* Ajusta pra frequencia 1 ser o valor zero. Economizando 1 bit. */
result = nbits;
result = result << 6;
result |= freq;
return result;
}
void decode_nbits_freq(int code, int* nbits, int* freq) {
*freq = TAKE_N_BITS_FROM(code, 0, 6);
*freq = *freq + 1;
*nbits = TAKE_N_BITS_FROM(code, 6, 5);
*nbits = *nbits ? *nbits : 32;
}
/*
* Salva o tamanho da imagem no arquivo compactado
*/
void setSize(FILE* file, int width, int height){
rewind(file);
fwrite(&width, 4, 1, file);
fwrite(&height, 4, 1, file);
}
/*
* Le o tamanho da imagem no arquivo compactado
*/
void getSize(FILE* file, int* width, int* height){
rewind(file);
fread(width, 4, 1, file);
fread(height, 4, 1, file);
#ifdef DEBUG4
printf("w: %d\n", *width);
printf("h: %d\n", *height);
#endif
}
/*
* Pega o tamanho em bits do "byte"
*/
int bit_size_of(int byte){
int i;
if (byte < 0) byte = -byte;
for (i=32; i>0; i--) {
if (TAKE_N_BITS_FROM(byte, i-1, 1)) {
return i;
}
}
return 1;
}
/*
* Insere os bits dentro do byte até completar 8 bits e o escreve no arquivo
*/
int write_bit(FILE* file, bool bit){
static unsigned char byte = 0x00;
static int pos=0;
byte <<= 1;
byte |= bit;
#ifdef DEBUG
printf("%d", bit);
#endif
if (pos == 7) {
#ifdef DEBUG3
printf("%X ", byte);
#endif
pos = 0;
fwrite(&byte, 1, 1, file);
byte = 0x00;
}
else {
pos++;
}
return pos;
}
void write_bit_flush(FILE* file) {
while (write_bit(file, 0)) {
}
}
/*
* Grava o byte no arquivo bit a bit
*/
void write_byte(FILE* file, int byte, unsigned int size){
int i;
bool bit;
if (byte < 0) {
byte = -byte;
write_bit(file, 1);
}
else {
write_bit(file, 0);
}
for (i=1; i<=size; i++) {
bit = TAKE_N_BITS_FROM(byte, size-i, 1);
write_bit(file, bit);
}
#ifdef DEBUG
printf(" ");
#endif
}
/*
* Grava o byte no arquivo bit a bit ignorando o sinal
*/
void write_unsigned_byte(FILE* file, int byte, unsigned int size){
int i;
bool bit;
for (i=1; i<=size; i++) {
bit = TAKE_N_BITS_FROM(byte, size-i, 1);
write_bit(file, bit);
}
#ifdef DEBUG
printf(" ");
#endif
}
/*
* Le cada bit do arquivo compactado
*/
bool read_bit(FILE* file){
static int pos=7;
static int byte;
bool bit;
if (pos < 7) {
pos++;
}
else {
pos = 0;
fread(&byte, 1, 1, file);
}
bit = TAKE_N_BITS_FROM(byte, 7, 1);
byte <<= 1;
return bit;
}
/*
* Separa os valores, gerando os bytes de cores
*/
unsigned char read_bits(FILE* file, int qtt){
int i;
unsigned char byte = 0x00;
bool negative;
negative = read_bit(file);
for (i=0; i<qtt; i++) {
byte <<= i?1:0;
byte |= read_bit(file);
}
if (negative) {
byte = -byte;
}
return byte;
}
/*
* Separa os valores, gerando os bytes de cores
*/
int read_bits2(FILE* file, int qtt){
int i;
int byte = 0;
bool negative;
negative = read_bit(file);
for (i=0; i<qtt; i++) {
byte <<= i?1:0;
byte |= read_bit(file);
}
if (negative) {
byte = -byte;
}
return byte;
}
#endif