REFACTOR: Completely remade the error handling format. Using pre-defined

error codes and error messages to make it easier to debug problems.
This commit is contained in:
2026-09-03 14:14:41 -04:00
parent ff25fad5ae
commit 56d26fe723
8 changed files with 188 additions and 67 deletions
+1
View File
@@ -17,3 +17,4 @@ AllowShortIfStatementsOnASingleLine: AllIfsAndElse
AllowShortLoopsOnASingleLine: true
IndentAccessModifiers: false # Indent access specifiers by one level
AccessModifierOffset: -4 # Optional: adjust offset relative to the class indentation level
# SpacesInBlockCommentsStyle: Always
+1 -1
View File
@@ -19,7 +19,7 @@ void
transcode_to_jpeg(PPM* in, JPEG* out);
void
transcode_to_ppm(JPEG* input, PPM* out);
transcode_to_ppm(JPEG* in, PPM* out);
PPM
inherit_from_jpeg(const JPEG* in, const char fmt);
+16
View File
@@ -21,6 +21,22 @@
#define SHIFT_16 16 /**< Constant shift of 16-Bits */
#define SHIFT_24 24 /**< Constant shift of 24-Bits */
#define SUCCESS 0
#define FAILURE 1
#define ERR_BUF_NULL 20
#define ERR_FILE_NULL 21
#define ERR_INVALID_SIZE 22
#define ERR_CREATION_FAIL 23
#define ERR_IMG_NULL 24
#define ERR_IMG_NAME_INVALID 25
#define ERR_JHEADER 26
extern const char* error_messages[];
#define LOG(msg) printf("LOG: %s\n", msg)
#define LOGERROR(error_code) printf("ERROR: %s\n", error_messages[error_code])
/**
*
* @brief Max value for any channel
+10 -9
View File
@@ -3,6 +3,8 @@
#include <stdio.h>
#include <stdlib.h>
#include "image/utils.h"
unsigned int
u32_put_alpha(const unsigned int clr, const unsigned char alpha)
{
@@ -103,10 +105,10 @@ u32_mask(const unsigned int clr, const char keep)
return clr & (BYTE_A | BYTE_B);
break;
default:
return 0;
return FAILURE;
break;
}
return 0;
return FAILURE;
}
unsigned int
@@ -114,11 +116,8 @@ u32_rotl(const unsigned int clr, const int n)
{
if (n > 8)
{
printf(
"ERROR: %i is greater than 8 results in black "
"pixels, please use values less than 8\n",
n);
exit(10);
LOGERROR(ERR_INVALID_SIZE);
return ERR_INVALID_SIZE;
}
unsigned int red = DECODE_R(clr);
unsigned int green = DECODE_G(clr);
@@ -261,13 +260,15 @@ box_blur(const unsigned int* src_buf, const PPM* img, const int radius)
unsigned int* first_pass = malloc(img->len * sizeof(unsigned int));
if (!first_pass)
{
return 0;
LOGERROR(ERR_BUF_NULL);
return NULL;
}
unsigned int* dst_buf = malloc(img->len * sizeof(unsigned int));
if (!dst_buf)
{
free(first_pass);
return 0;
LOGERROR(ERR_BUF_NULL);
return NULL;
}
for (int y = 0; y < img->height; y++)
{
+88 -39
View File
@@ -4,20 +4,21 @@
#include <stdlib.h>
#include <turbojpeg.h>
#include "image/utils.h"
unsigned int*
ppm_load(const char* file, PPM* m_attr)
{
printf("Starting decode...\n");
unsigned char red;
unsigned char green;
unsigned char blue;
LOG("Decoding");
unsigned char red, green, blue;
char fmt[3];
int max_val;
FILE* fptr;
fptr = fopen(file, "r");
if (!fptr)
{
printf("Invalid file name: %s\n", file);
LOGERROR(ERR_IMG_NAME_INVALID);
LOG(file);
return NULL;
}
fscanf(fptr, "%s", fmt);
@@ -29,12 +30,14 @@ ppm_load(const char* file, PPM* m_attr)
unsigned char* img_buf = malloc(m_attr->len * 3);
if (!img_buf)
{
LOGERROR(ERR_BUF_NULL);
return NULL;
}
unsigned int* clr_buf = malloc(m_attr->len * sizeof(unsigned int));
if (!clr_buf)
{
free(img_buf);
LOGERROR(ERR_BUF_NULL);
return NULL;
}
if (m_attr->fmt == '3')
@@ -60,7 +63,7 @@ ppm_load(const char* file, PPM* m_attr)
fclose(fptr);
free(img_buf);
printf("Decoding done!\n");
LOG("Decoding Finished");
return clr_buf;
}
@@ -69,15 +72,16 @@ ppm_save(const unsigned int* buf, const PPM img, char* name)
{
if (!buf)
{
return 10;
LOGERROR(ERR_BUF_NULL);
return ERR_BUF_NULL;
}
unsigned char red, green, blue;
unsigned char* dst_buf = malloc(img.len * 3);
if (!dst_buf)
{
return 10;
LOGERROR(ERR_BUF_NULL);
return ERR_BUF_NULL;
}
printf("Starting encode...\n");
LOG("Encoding");
FILE* fptr;
if (img.fmt == '3')
@@ -93,7 +97,8 @@ ppm_save(const unsigned int* buf, const PPM img, char* name)
if (!fptr)
{
free(dst_buf);
return 10;
LOGERROR(ERR_FILE_NULL);
return ERR_FILE_NULL;
}
fprintf(fptr, "P%c\n%d %d\n255\n", img.fmt, img.width, img.height);
@@ -101,10 +106,8 @@ ppm_save(const unsigned int* buf, const PPM img, char* name)
{
for (int i = 0; i < img.len; i++)
{
red = DECODE_R(buf[i]);
green = DECODE_G(buf[i]);
blue = DECODE_B(buf[i]);
fprintf(fptr, "%d %d %d ", red, green, blue);
fprintf(fptr, "%d %d %d ", DECODE_R(buf[i]),
DECODE_G(buf[i]), DECODE_B(buf[i]));
if (i % 7 == 0)
{
fprintf(fptr, "\n");
@@ -124,20 +127,20 @@ ppm_save(const unsigned int* buf, const PPM img, char* name)
}
fclose(fptr);
free(dst_buf);
printf("Encode Done!\n");
printf("Image: %s is saved.\n", name);
return 1;
LOG("Encoding Finished");
return SUCCESS;
}
unsigned int*
jpeg_load(JPEG* m_attr)
{
printf("Starting Decode...\n");
LOG("Decoding");
tjhandle tjdecompress = tj3Init(TJINIT_DECOMPRESS);
unsigned char* jpeg_buf = NULL;
FILE* infile = fopen(m_attr->name, "rb");
if (!infile)
{
LOGERROR(ERR_FILE_NULL);
return NULL;
}
fseek(infile, 0, SEEK_END);
@@ -148,26 +151,33 @@ jpeg_load(JPEG* m_attr)
fclose(infile);
if (tj3DecompressHeader(tjdecompress, jpeg_buf, m_attr->len) < 0)
{
printf("Header error: %s\n", tj3GetErrorStr(tjdecompress));
LOGERROR(ERR_JHEADER);
LOG(tj3GetErrorStr(tjdecompress));
free(jpeg_buf);
return NULL;
}
m_attr->width = tj3Get(tjdecompress, TJPARAM_JPEGWIDTH);
m_attr->height = tj3Get(tjdecompress, TJPARAM_JPEGHEIGHT);
m_attr->len = m_attr->width * m_attr->height;
unsigned int* pixels =
malloc(m_attr->width * m_attr->height * sizeof(unsigned int));
if (!pixels)
{
LOGERROR(ERR_BUF_NULL);
return NULL;
}
tj3Decompress8(tjdecompress, jpeg_buf, m_attr->len,
(unsigned char*)pixels, 0, TJPF_BGRA);
tj3Destroy(tjdecompress);
free(jpeg_buf);
printf("Decode Successful!\n");
LOG("Decoding Finished");
return pixels;
}
int
jpeg_save(const unsigned int* src_buf, const JPEG* attr, const char* name)
{
printf("Starting Decode...\n");
LOG("Encoding");
tjhandle tjcompress = tj3Init(TJINIT_COMPRESS);
unsigned char* dst_buf = NULL;
size_t dst_size = 0;
@@ -176,27 +186,52 @@ jpeg_save(const unsigned int* src_buf, const JPEG* attr, const char* name)
if (tj3Compress8(tjcompress, (unsigned char*)src_buf, attr->width, 0,
attr->height, TJPF_BGRA, &dst_buf, &dst_size) < 0)
{
printf("TurboJPEG Error: %s\n", tj3GetErrorStr(tjcompress));
LOGERROR(ERR_JHEADER);
LOG(tj3GetErrorStr(tjcompress));
return ERR_JHEADER;
}
FILE* fptr = fopen(name, "wb");
if (!fptr || dst_buf == NULL || dst_size <= 0)
if (!fptr)
{
tj3Free(dst_buf);
return 25;
LOGERROR(ERR_FILE_NULL);
return ERR_FILE_NULL;
}
if (dst_buf == NULL)
{
tj3Free(dst_buf);
LOGERROR(ERR_BUF_NULL);
return ERR_BUF_NULL;
}
if (dst_size <= 0)
{
tj3Free(dst_buf);
LOGERROR(ERR_INVALID_SIZE);
return ERR_INVALID_SIZE;
}
fwrite(dst_buf, 1, dst_size, fptr);
fclose(fptr);
tj3Destroy(tjcompress);
tj3Free(dst_buf);
printf("Encode Successful!\n");
return 1;
LOG("Encoding Finished");
return SUCCESS;
}
void
transcode_to_jpeg(PPM* in, JPEG* out)
{
if (!in || !out)
{
LOGERROR(ERR_IMG_NULL);
return;
}
unsigned int* dst = ppm_load(in->name, in);
if (!dst)
{
LOGERROR(ERR_BUF_NULL);
return;
}
out->width = in->width;
out->height = in->height;
jpeg_save(dst, out, out->name);
@@ -204,11 +239,21 @@ transcode_to_jpeg(PPM* in, JPEG* out)
}
void
transcode_to_ppm(JPEG* input, PPM* out)
transcode_to_ppm(JPEG* in, PPM* out)
{
unsigned int* dst = jpeg_load(input);
out->width = input->width;
out->height = input->height;
if (!in || !out)
{
LOGERROR(ERR_IMG_NULL);
return;
}
unsigned int* dst = jpeg_load(in);
if (!dst)
{
LOGERROR(ERR_BUF_NULL);
return;
}
out->width = in->width;
out->height = in->height;
out->len = out->width * out->height;
ppm_save(dst, *out, out->name);
free(dst);
@@ -217,6 +262,12 @@ transcode_to_ppm(JPEG* input, PPM* out)
PPM
inherit_from_jpeg(const JPEG* in, const char fmt)
{
PPM img;
if (!in)
{
LOGERROR(ERR_IMG_NULL);
return img;
}
PPM image = { .name = in->name,
.width = in->width,
.height = in->height,
@@ -228,6 +279,12 @@ inherit_from_jpeg(const JPEG* in, const char fmt)
JPEG
inherit_from_ppm(const PPM* in)
{
JPEG blank;
if (!in)
{
LOGERROR(ERR_IMG_NULL);
return blank;
}
JPEG image = {
.name = in->name,
.width = in->width,
@@ -236,11 +293,3 @@ inherit_from_ppm(const PPM* in)
};
return image;
}
/** The Second image gets merged into the first.
* The First image obtains attributes from the second image that were not found.
*/
// PPM
// merge_ppm(const PPM* in_1, const PPM* in_2) {
// if(in)
// }
+34 -7
View File
@@ -12,7 +12,7 @@
* Keep in mind any function that creates a new buffer and returns it can
* overwrite the old one, however it is lost. SO create a new variable and free
* the old one after use.
* */
*/
int
main()
{
@@ -20,19 +20,46 @@ main()
// .name = "../MF8jno.jpg",
//
// };
// JPEG img_j = {
// .name = "../assets/test_2.jpg",
// };
//
// unsigned int* buffer = jpeg_load(&img_j);
// PPM out = inherit_from_jpeg(&img_j, '3');
// print_attr(&out);
//
// ppm_save(buffer, out, "../assets/test_2.ppm");
// free(buffer);
PPM img = {
.name = "../assets/test.ppm",
.name = "../assets/test_2.ppm",
};
// unsigned int* buf = ppm_load(img.name, &img);
// unsigned int* box = box_blur(buf, &img, 20);
// free(buf);
img.fmt = '3';
unsigned int* buf = ppm_load(img.name, &img);
if (!buf)
{
return ERR_BUF_NULL;
}
unsigned int* blur = box_blur(buf, &img, 20);
free(buf);
if (!blur)
{
return ERR_BUF_NULL;
}
for (int i = 0; i < img.len; i++)
{
// you need to replace the old value with the new updated value
buf[i] = u32_contrast(buf[i], 9);
blur[i] = u32_rotl(blur[i], 4);
}
img.fmt = '3';
// buf = u32_rotate(buf, &img);
ppm_save(buf, img, "../assets/test_new.ppm");
ppm_save(blur, img, "../assets/test_2_new.ppm");
free(blur);
// // buf = u32_rotate(buf, &img);
// ppm_save(box, img, "../assets/test_new.ppm");
// free(box);
// PPM out_2 = inherit_from_jpeg(&out_1, '6');
//
+15 -1
View File
@@ -1,17 +1,22 @@
#include "image/transformations.h"
#include <stdio.h>
#include <stdlib.h>
#include "image/utils.h"
unsigned int*
ppm_flip_h(const unsigned int* buf, const PPM img)
{
if (!buf)
{
LOGERROR(ERR_BUF_NULL);
return NULL;
}
unsigned int* flip = malloc(img.len * sizeof(unsigned int));
if (!flip)
{
LOGERROR(ERR_CREATION_FAIL);
return NULL;
}
int idx = 0;
@@ -33,11 +38,13 @@ ppm_flip_v(const unsigned int* buf, const PPM img)
{
if (!buf)
{
LOGERROR(ERR_BUF_NULL);
return NULL;
}
unsigned int* flip = malloc(img.len * sizeof(unsigned int));
if (!flip)
{
LOGERROR(ERR_FILE_NULL);
return NULL;
}
@@ -58,13 +65,20 @@ ppm_flip_v(const unsigned int* buf, const PPM img)
unsigned int*
u32_rotate(const unsigned int* buf, PPM* m_img)
{
if (!buf || !m_img)
if (!buf)
{
LOGERROR(ERR_BUF_NULL);
return NULL;
}
if (!m_img)
{
LOGERROR(ERR_IMG_NULL);
return NULL;
}
unsigned int* mask = malloc(m_img->len * sizeof(unsigned int));
if (!mask)
{
LOGERROR(ERR_BUF_NULL);
return NULL;
}
int old_width = m_img->width;
+23 -10
View File
@@ -1,6 +1,19 @@
#include "image/utils.h"
#include <stdio.h>
const char* error_messages[] = {
[ERR_BUF_NULL] = "Buffer NULL",
[ERR_FILE_NULL] = "File NULL",
[ERR_CREATION_FAIL] = "Buffer creation failed",
[ERR_INVALID_SIZE] = "Given size is invalid",
[ERR_IMG_NULL] = "Image NULL",
[ERR_IMG_NAME_INVALID] = "Invalid File Name",
[ERR_JHEADER] = "Header Error:",
#define ERR_JHEADER 26
};
unsigned long
u32to_u64(const unsigned int clr)
{
@@ -23,16 +36,16 @@ u64to_u32(const unsigned long clr, const unsigned long u64_div)
(b / u64_div));
}
void
__attribute__((overloadable))
print_attr(const PPM *src) {
printf("Name: %s\nFMT: %c\nWidth: %i, Height: %i\nLength: %i\n",
src->name, src->fmt, src->width, src->height, src->len);
void __attribute__((overloadable))
print_attr(const PPM* src)
{
printf("Name: %s\nFMT: %c\nWidth: %i, Height: %i\nLength: %i\n",
src->name, src->fmt, src->width, src->height, src->len);
}
void
__attribute__((overloadable))
print_attr(const JPEG *src) {
printf("Name: %s\nWidth: %i, Height: %i\nLength: %i\n",
src->name, src->width, src->height, src->len);
void __attribute__((overloadable))
print_attr(const JPEG* src)
{
printf("Name: %s\nWidth: %i, Height: %i\nLength: %i\n", src->name,
src->width, src->height, src->len);
}