Skip to content
Permalink
Browse files

Add ReadData subroutines for uint32_t uint16_t and uint8_t

  • Loading branch information
heapsmash committed Oct 13, 2019
1 parent 1bc5694 commit 5861036288ce3fbaee96ed53b7058583bab7548b
Showing with 101 additions and 76 deletions.
  1. +74 −55 bmp.c
  2. +27 −6 bmp.h
  3. +0 −14 syscalls.c
  4. +0 −1 syscalls.h
129 bmp.c
@@ -43,8 +43,8 @@
int main(int argc, char *argv[], char *envp[])
{
int opt;
void (*WriteDataToArray)(BitRipTools *) = NULL;
BitRipTools bitmap;
uint32_t (*SwapEndian)(uint32_t);

bitmap.ncols_per_row = 1;
bitmap.file_name_to_read = bitmap.array_name_to_store = bitmap.file_name_to_save = NULL;
@@ -86,21 +86,19 @@ int main(int argc, char *argv[], char *envp[])

ReadBitmapHeader(&bitmap);
switch (bitmap.header.width_px) {
case 32:
SwapEndian = Swap32;
break;
case 16:
SwapEndian = Swap16;
WriteDataToArray = ReadDataUint16;
break;
case 8:
SwapEndian = Swap8;
WriteDataToArray = ReadDataUint8;
break;
default:
PRINT_ERR_AND_RETURN("Width must be 1bpp at 8px 16px 32px")
WriteDataToArray = ReadDataUint32;
break;
}

WriteCommentToFile(bitmap);
WriteArrayToFile(&bitmap, SwapEndian);
WriteDataToArray(&bitmap);

Close(bitmap.bitmap_to_read_fd);
Close(bitmap.c_file_to_write_fd);
@@ -109,46 +107,85 @@ int main(int argc, char *argv[], char *envp[])
}


void WriteArrayToFile(BitRipTools *data, uint32_t(*Swap)(uint32_t))
void ReadDataUint8(BitRipTools *data)
{
int i, n_nibbles;
char *format, *format_end;
int nread;
uint32_t *temp_data = calloc((data->header.height_px * data->header.width_px) + 1, 1);

uint32_t hex_image_data[data->header.height_px];
if (Lseek(data->bitmap_to_read_fd, data->header.offset, SEEK_SET) != data->header.offset) {
PRINT_ERR_AND_EXIT("Lseek failed")
}

n_nibbles = data->header.width_px / 4;
nread = IoRead(data->bitmap_to_read_fd, temp_data, data->header.image_size_bytes);
if (nread < 0) {
PRINT_ERRNO_AND_EXIT("IoRead error")
}
nread >>= 2;

switch (n_nibbles) {
case 2: /* uint8_t */
format = "\t0x%02x,";
format_end = "\t0x%02x\n";
break;
case 4: /* uint16_t */
format = "\t0x%04x,";
format_end = "\t0x%04x\n";
break;
case 8: /* uint32_t */
format = "\t0x%08x,";
format_end = "\t0x%08x\n";
break;
default:
return;
Print(data->c_file_to_write_fd, "const uint%d %s[] = {\n", data->header.width_px, data->array_name_to_store);
for (nread = nread - 1; nread >= 0; nread--) {
temp_data[nread] = ~temp_data[nread];
temp_data[nread] = temp_data[nread] & 0x000000ff;
printf("0x%02x,\n", temp_data[nread]);
}
}


void ReadDataUint16(BitRipTools *data)
{
int nread;
uint32_t *temp_data = calloc((data->header.height_px * data->header.width_px) + 1, 1);

if (Lseek(data->bitmap_to_read_fd, data->header.offset, SEEK_SET) != data->header.offset) {
PRINT_ERR_AND_EXIT("Lseek failed")
}

nread = IoRead(data->bitmap_to_read_fd, temp_data, data->header.image_size_bytes);
if (nread < 0) {
PRINT_ERRNO_AND_EXIT("IoRead error")
}
nread >>= 2;

Print(data->c_file_to_write_fd, "const uint%d %s[] = {\n", data->header.width_px, data->array_name_to_store);
for (i = data->header.height_px - 1; i > 0; i--) { /* vertically flip bitmap */
Read(data->bitmap_to_read_fd, &hex_image_data[i], n_nibbles);
hex_image_data[i] = Swap((~hex_image_data[i])); /* negate, then correct endian */
Print(data->c_file_to_write_fd, format, hex_image_data[i]);
if (i % data->ncols_per_row == 0)
for (nread = nread - 1; nread >= 0; nread--) {
temp_data[nread] = ENDIAN16(temp_data[nread]);
temp_data[nread] = ~temp_data[nread];
temp_data[nread] &= 0x0000ffff;
printf("0x%04x,\n", temp_data[nread]);
}
}


void ReadDataUint32(BitRipTools *data)
{
int nread;
uint32_t *temp_data = calloc((data->header.height_px * data->header.width_px) + 1, 1);

if (Lseek(data->bitmap_to_read_fd, data->header.offset, SEEK_SET) != data->header.offset) {
PRINT_ERR_AND_EXIT("Lseek failed")
}

nread = IoRead(data->bitmap_to_read_fd, temp_data, data->header.image_size_bytes);
if (nread < 0) {
PRINT_ERRNO_AND_EXIT("IoRead error")
}
nread >>= 2;
Print(data->c_file_to_write_fd, "const unsigned int g_%s_height = %d;\t/* height in bits */ \n", data->array_name_to_store,
data->header.height_px);
Print(data->c_file_to_write_fd, "const unsigned int g_%s_width = %d;\t/* width in bits */\n", data->array_name_to_store, data->header.width_px);
Print(data->c_file_to_write_fd, "const unsigned int g_%s_size = %d;\t/* total bytes */\n\n", data->array_name_to_store,
data->header.image_size_bytes);

Print(data->c_file_to_write_fd, "const uint32_t %s[] = {\n", data->array_name_to_store);
for (nread = nread - 1; nread > 0; nread--) {
temp_data[nread] = ENDIAN32(temp_data[nread]);
temp_data[nread] = ~temp_data[nread];
Print(data->c_file_to_write_fd, "\t0x%08x,", temp_data[nread]);
if (nread % data->ncols_per_row == 0)
Print(data->c_file_to_write_fd, "\n");
}

Print(data->c_file_to_write_fd, format_end, hex_image_data[i]);
Print(data->c_file_to_write_fd, "\t0x%08x\n", temp_data[nread]);
Print(data->c_file_to_write_fd, "}; /* Generated with BitRip */ \n\n");
}

@@ -197,39 +234,21 @@ void WriteCommentToFile(BitRipTools data)
data.header.important_colors
};

Print(data.c_file_to_write_fd, "/*\tCopyright (c) 2019, Michael S. Walker <sigmatau@heapsmash.com>\n");
Print(data.c_file_to_write_fd, "/*\tBitRip Copyright (c) 2019, Michael S. Walker <sigmatau@heapsmash.com>\n");
Print(data.c_file_to_write_fd, " *\tAll Rights Reserved in all Federations, including Alpha Centauris.\n");
Print(data.c_file_to_write_fd, " *\n");
Print(data.c_file_to_write_fd, " *\t.--.https://github.com/heapsmash/Monochrome-Bitmap-Converter-----------.\n");
Print(data.c_file_to_write_fd, " *\t| | Header Name | Value | Description |\n");
Print(data.c_file_to_write_fd, " *\t:--+-------------------+-------+---------------------------------------:\n");
Print(data.c_file_to_write_fd, " *\t| | %-17s | %-5x | %-37s |\n", g_header_names[0], header_values[0], g_header_description[0]);
Print(data.c_file_to_write_fd, " *\t:--+-------------------+-------+---------------------------------------:\n");
for (i = 1; i < data.header.height_px; i++) {

for (i = 1; i < sizeof header_values / sizeof(int); i++) {
Print(data.c_file_to_write_fd, " *\t| | %-17s | %-5d | %-37s |\n", g_header_names[i], header_values[i], g_header_description[i]);
Print(data.c_file_to_write_fd, " *\t:--+-------------------+-------+---------------------------------------:\n");
}
Print(data.c_file_to_write_fd, " */\n\n");
}


uint32_t Swap32(uint32_t x)
{
return ((((x >> 24) & 0x000000FF) | (((x >> 8) & 0x0000FF00) | (((x << 8) & 0x00FF0000) | (((x << 24) & 0xFF000000))))));
}


uint32_t Swap16(uint32_t x)
{

return ((((x) >> 8) & 0x00FF) | (((x) << 8) & 0xFF00));
}


uint32_t Swap8(uint32_t x)
{
return x;
}


#pragma clang diagnostic pop
33 bmp.h
@@ -31,6 +31,28 @@

#include <stdint.h> /* for uintxx_t */
#include <errno.h> /* for CHECK_SIZE */
#include <endian.h>

#if __BYTE_ORDER == __BIG_ENDIAN

#define ENDIAN16(val) val
#define ENDIAN32(val) val
#define ENDIAN64(val) val
#else

#define ENDIAN16(val) \
( (((val) >> 8) & 0x00FF) | (((val) << 8) & 0xFF00) )

#define ENDIAN32(val) \
( (((val) >> 24) & 0x000000FF) | (((val) >> 8) & 0x0000FF00) | \
(((val) << 8) & 0x00FF0000) | (((val) << 24) & 0xFF000000) )

#define ENDIAN64(val) \
( (((val) >> 56) & 0x00000000000000FF) | (((val) >> 40) & 0x000000000000FF00) | \
(((val) >> 24) & 0x0000000000FF0000) | (((val) >> 8) & 0x00000000FF000000) | \
(((val) << 8) & 0x000000FF00000000) | (((val) << 24) & 0x0000FF0000000000) | \
(((val) << 40) & 0x00FF000000000000) | (((val) << 56) & 0xFF00000000000000) )
#endif

#if defined(__linux__) && defined(__x86_64__)

@@ -115,12 +137,11 @@ typedef struct _BMPImageTools {
char *file_name_to_save, *file_name_to_read, *array_name_to_store;
} BitRipTools;

uint32_t Swap8(uint32_t x);
uint32_t Swap16(uint32_t x);
uint32_t Swap32(uint32_t x);

void WriteArrayToFile(BitRipTools *data, uint32_t(*Swap)(uint32_t));
void WriteCommentToFile(BitRipTools data);
void ReadBitmapHeader(BitRipTools *data);

void ReadDataUint8(BitRipTools *data);
void ReadDataUint16(BitRipTools *data);
void ReadDataUint32(BitRipTools *data);
uint32_t rotr32(uint32_t n, unsigned int c);
uint32_t rotl32(uint32_t n, unsigned int c);
#endif //BMP_RIP_BMP_H
@@ -99,20 +99,6 @@ ssize_t Read(int fd, void *buf, size_t count)
}


ssize_t Write(int fd, const void *buf, size_t count)
{
ssize_t n_written = syscall(SYS_write, fd, buf, count);

if (n_written >= 0)
return n_written;

if (errno == EINTR) /* Interrupted by sig handler return */
return -1;

PRINT_ERRNO_AND_EXIT("Write error") /* errno set by Write() */
}


off_t Lseek(int fd, off_t offset, int whence)
{
off_t result_offset = syscall(SYS_lseek, fd, offset, whence);
@@ -45,7 +45,6 @@

/* Syscall wrappers */
int Open(const char *file_name, mode_t arg_flags, ...);
ssize_t Write(int fd, const void *buf, size_t count);
void Print(int file_handle, const char *fmt, ...);
ssize_t IoRead(int fd, void *usrbuf, size_t n);
ssize_t Read(int fd, void *buf, size_t count);

0 comments on commit 5861036

Please sign in to comment.
You can’t perform that action at this time.