Initial commit / Day0
This commit is contained in:
commit
a9ffeca886
|
@ -0,0 +1,104 @@
|
|||
#ifndef _HEXDUMP_H_
|
||||
#define _HEXDUMP_H_
|
||||
#include <stdlib.h>
|
||||
#include <stdint.h>
|
||||
void hexdump(void *data, size_t len);
|
||||
void rgbdump(void *data, uint16_t w, uint16_t h);
|
||||
void rgbadump(void *data, uint16_t w, uint16_t h);
|
||||
#endif
|
||||
|
||||
#ifdef HEXDUMP_IMPLEMENTATION
|
||||
#if !defined(HEXDUMP_COLORS0) && !defined(HEXDUMP_COLORS1)
|
||||
#define HEXDUMP_N_COLORS 8
|
||||
const uint8_t hexdump_colors[2][8] = {
|
||||
{ 197, 215, 227, 47, 39, 57, 135, 92 },
|
||||
{ 124, 214, 226, 46, 31, 55, 127, 53 },
|
||||
};
|
||||
#else
|
||||
#define HEXDUMP_RAINBOW
|
||||
#ifndef HEXDUMP_N_COLORS
|
||||
#define HEXDUMP_N_COLORS 8
|
||||
#endif
|
||||
const uint8_t hexdump_colors[2][HEXDUMP_N_COLORS] = {
|
||||
HEXDUMP_COLORS0,
|
||||
HEXDUMP_COLORS1,
|
||||
};
|
||||
#endif
|
||||
#include <stdio.h>
|
||||
void hexdump(void *data, size_t len)
|
||||
{
|
||||
uint8_t *ptr = data;
|
||||
for (size_t i = 0; i < len;)
|
||||
{
|
||||
#ifdef HEXDUMP_RAINBOW
|
||||
printf("\033[%dm%08zx\033[0m\t", ((i >> 4) & 1 ? 90 : 37), i);
|
||||
#else
|
||||
printf("%08zx\t", i);
|
||||
#endif
|
||||
for (int x = 0; x < 16; x++)
|
||||
{
|
||||
#ifdef HEXDUMP_RAINBOW
|
||||
printf("\033[38;5;%dm",
|
||||
hexdump_colors[(i >> 4) & 1][(x + i) % HEXDUMP_N_COLORS]);
|
||||
#endif
|
||||
if (i + x >= len) printf("-- ");
|
||||
else printf("%02x ", ptr[i + x]);
|
||||
#ifdef HEXDUMP_RAINBOW
|
||||
printf("\033[0m");
|
||||
#endif
|
||||
if (x % 4 == 3) printf("\t");
|
||||
}
|
||||
#ifdef HEXDUMP_PRINTABLE
|
||||
for (int x = 0; x < 16; x++)
|
||||
{
|
||||
if (i + x >= len) break;
|
||||
#ifdef HEXDUMP_RAINBOW
|
||||
printf("\033[38;5;%dm",
|
||||
hexdump_colors[(i >> 4) & 1][(x + i) % HEXDUMP_N_COLORS]);
|
||||
#endif
|
||||
if (isprint(ptr[i + x]))
|
||||
putchar(ptr[i + x]);
|
||||
else
|
||||
putchar('.');
|
||||
#ifdef HEXDUMP_RAINBOW
|
||||
printf("\033[0m");
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
printf("\n");
|
||||
i += 16;
|
||||
}
|
||||
}
|
||||
|
||||
void rgbdump(void *data, uint16_t w, uint16_t h)
|
||||
{
|
||||
uint8_t *ptr = data;
|
||||
for (int y = 0; y < h; y += 2)
|
||||
{
|
||||
for (int x = 0; x < w; x++)
|
||||
{
|
||||
int i1 = x + y * w, i2 = x + (y + 1) * w;
|
||||
printf("\033[38;2;%d;%d;%d;48;2;%d;%d;%dm\xe2\x96\x80",
|
||||
ptr[i1 * 3 + 0], ptr[i1 * 3 + 1], ptr[i1 * 3 + 2],
|
||||
ptr[i2 * 3 + 0], ptr[i2 * 3 + 1], ptr[i2 * 3 + 2]);
|
||||
}
|
||||
printf("\033[0m\n");
|
||||
}
|
||||
}
|
||||
|
||||
void rgbadump(void *data, uint16_t w, uint16_t h)
|
||||
{
|
||||
uint8_t *ptr = data;
|
||||
for (int y = 0; y < h; y += 2)
|
||||
{
|
||||
for (int x = 0; x < w; x++)
|
||||
{
|
||||
int i1 = x + y * w, i2 = x + (y + 1) * w;
|
||||
printf("\033[38;2;%d;%d;%d;48;2;%d;%d;%dm\xe2\x96\x80",
|
||||
ptr[i1 * 4 + 0], ptr[i1 * 4 + 1], ptr[i1 * 4 + 2],
|
||||
ptr[i2 * 4 + 0], ptr[i2 * 4 + 1], ptr[i2 * 4 + 2]);
|
||||
}
|
||||
printf("\033[0m\n");
|
||||
}
|
||||
}
|
||||
#endif
|
|
@ -0,0 +1,195 @@
|
|||
// x-run: gcc % -o main -g && ./main /home/hkc/images/wallpapers/photo_2020-09-18_10-05-14.jpg
|
||||
|
||||
#include <endian.h>
|
||||
#include <stdio.h>
|
||||
#include <stdint.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
#include <errno.h>
|
||||
#include <ctype.h>
|
||||
#define HEXDUMP_RAINBOW
|
||||
#define HEXDUMP_PRINTABLE
|
||||
#define HEXDUMP_IMPLEMENTATION
|
||||
#include "./hexdump.h"
|
||||
|
||||
typedef uint16_t marker_t;
|
||||
|
||||
typedef enum {
|
||||
SOF0 = 0xFFC0, // Baseline DCT
|
||||
SOF1 = 0xFFC1, // Extended seq DCT
|
||||
SOF2 = 0xFFC2, // Progressive DCT
|
||||
SOF3 = 0xFFC3, // Lossless
|
||||
DHT = 0xFFC4, // Define Huffman Table
|
||||
SOF5 = 0xFFC5, //
|
||||
SOF6 = 0xFFC6,
|
||||
SOF7 = 0xFFC7,
|
||||
JPG = 0xFFC8,
|
||||
SOF9 = 0xFFC9,
|
||||
SOF10 = 0xFFCA,
|
||||
SOF11 = 0xFFCB,
|
||||
DAC = 0xFFCC,
|
||||
SOF13 = 0xFFCD,
|
||||
SOF14 = 0xFFCE,
|
||||
SOF15 = 0xFFCF,
|
||||
|
||||
|
||||
} marker_type_t;
|
||||
|
||||
struct JFIF_SOF0_Component {
|
||||
uint8_t id;
|
||||
uint8_t TODO_0 : 4;
|
||||
uint8_t TODO_1 : 4;
|
||||
} __attribute__((packed));
|
||||
|
||||
struct JFIF_SOF0 {
|
||||
uint16_t bit_depth;
|
||||
uint16_t height;
|
||||
uint8_t width;
|
||||
uint8_t n_components;
|
||||
struct JFIF_SOF0_Component *components;
|
||||
} __attribute__((packed));
|
||||
|
||||
#define panic(...) { \
|
||||
fprintf(stderr, "!PANIC! at %s:%d\n", __FILE__, __LINE__);\
|
||||
fprintf(stderr, __VA_ARGS__); \
|
||||
fprintf(stderr, "\nerrno=%d (%s)\n", errno, strerror(errno)); \
|
||||
abort(); \
|
||||
}
|
||||
|
||||
marker_t read_and_print_block(FILE *fp);
|
||||
const char *marker_name(int marker);
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
static uint8_t tmp[8192];
|
||||
FILE *fp = fopen(argv[1], "rb");
|
||||
fread(tmp, 1, 2, fp);
|
||||
if (memcmp(tmp, "\xFF\xD8", 2)) {
|
||||
panic("Invalid header!");
|
||||
}
|
||||
|
||||
marker_t last_marker;
|
||||
do {
|
||||
last_marker = read_and_print_block(fp);
|
||||
} while (last_marker != 0xFFD9);
|
||||
}
|
||||
|
||||
|
||||
marker_t read_and_print_block(FILE *fp) {
|
||||
static uint8_t buffer[65536];
|
||||
marker_t marker;
|
||||
uint16_t length;
|
||||
|
||||
long int pos = ftell(fp);
|
||||
|
||||
fread(&marker, sizeof(marker_t), 1, fp);
|
||||
marker = be16toh(marker);
|
||||
|
||||
if ((marker & 0xFF00) != 0xFF00) {
|
||||
printf("!!!!!!!!\n");
|
||||
fseek(fp, pos & ~0xF, SEEK_SET);
|
||||
fread(buffer, 1, 32, fp);
|
||||
hexdump(buffer, 32);
|
||||
panic("Invalid marker %04x at %ld (0x%lx)", marker, pos, pos);
|
||||
}
|
||||
|
||||
if (marker == 0xFFD9) return marker;
|
||||
|
||||
fread(&length, sizeof(uint16_t), 1, fp);
|
||||
length = be16toh(length) - 2;
|
||||
printf("marker: %04x %8s (%d long) at %ld %lx\n", marker, marker_name(marker), length, pos, pos);
|
||||
|
||||
fread(buffer, 1, length, fp);
|
||||
|
||||
switch (marker) {
|
||||
case SOF0:
|
||||
printf("\033[91mSTART OF FRAME\033[0m\n");
|
||||
hexdump(buffer, length);
|
||||
break;
|
||||
|
||||
case 0xFFDA: // Start Of Scan
|
||||
{
|
||||
uint8_t n_components = buffer[0];
|
||||
uint8_t *cur = &buffer[1];
|
||||
|
||||
printf("components: %d\n", n_components);
|
||||
for (uint8_t i = 0; i < n_components; i++) {
|
||||
uint8_t selector = *cur++,
|
||||
tables = *cur++;
|
||||
printf("\t%d: %d in %d/%d\n", i, selector, tables >> 4, tables & 0xf);
|
||||
}
|
||||
uint8_t spectral_selector_start = *cur++,
|
||||
spectral_selector_end = *cur++,
|
||||
successive_approx = *cur++;
|
||||
printf("spectral selector: %d..%d\n", spectral_selector_start, spectral_selector_end);
|
||||
|
||||
int n_read = -1;
|
||||
do {
|
||||
n_read++;
|
||||
fread(&buffer[n_read], 1, 1, fp);
|
||||
} while (!(buffer[n_read - 1] == 0xFF && (buffer[n_read] & 0xF0) == 0xF0));
|
||||
printf("stopped after %d bytes\n", n_read);
|
||||
hexdump(buffer, n_read);
|
||||
fseek(fp, ftell(fp) - 1, SEEK_SET);
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xFFDB: // Quantization table
|
||||
{
|
||||
uint8_t destination = buffer[0];
|
||||
printf("\tdestination: %d\n", destination);
|
||||
for (int y = 0; y < 8; y++) {
|
||||
printf("\t");
|
||||
for (int x = 0; x < 8; x++) {
|
||||
printf("%3d ", buffer[1 + x + y * 8]);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
||||
case 0xFFE0: // APP*
|
||||
case 0xFFE1:
|
||||
case 0xFFE2:
|
||||
case 0xFFE3:
|
||||
case 0xFFE4:
|
||||
case 0xFFE5:
|
||||
case 0xFFE6:
|
||||
case 0xFFE7:
|
||||
case 0xFFE8:
|
||||
case 0xFFE9:
|
||||
case 0xFFEA:
|
||||
case 0xFFEB:
|
||||
case 0xFFEC:
|
||||
case 0xFFED:
|
||||
case 0xFFEE:
|
||||
case 0xFFEF:
|
||||
break;
|
||||
default:
|
||||
hexdump(buffer, length);
|
||||
break;
|
||||
}
|
||||
|
||||
return marker;
|
||||
}
|
||||
|
||||
const char *marker_name(int marker) {
|
||||
switch (marker) {
|
||||
case SOF0: return " SOF0";
|
||||
case SOF1: return " SOF1";
|
||||
case SOF2: return " SOF2";
|
||||
case SOF3: return " SOF3";
|
||||
case DHT: return " DHT";
|
||||
case SOF5: return " SOF5";
|
||||
case SOF6: return " SOF6";
|
||||
case SOF7: return " SOF7";
|
||||
case JPG: return " JPG";
|
||||
case SOF9: return " SOF9";
|
||||
case SOF10: return "SOF10";
|
||||
case SOF11: return "SOF11";
|
||||
case DAC: return " DAC";
|
||||
case SOF13: return "SOF13";
|
||||
case SOF14: return "SOF14";
|
||||
case SOF15: return "SOF15";
|
||||
default: return "N/A";
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue