]> git.seodisparate.com - c_simple_http/commitdiff
Refactor http_template to use String_Part
authorStephen Seo <seo.disparate@gmail.com>
Mon, 23 Sep 2024 05:09:25 +0000 (14:09 +0900)
committerStephen Seo <seo.disparate@gmail.com>
Mon, 23 Sep 2024 05:09:25 +0000 (14:09 +0900)
src/helpers.c
src/helpers.h
src/http_template.c

index 4744c4915eafa9ae2ba6e55f3c9d620781b2543d..b2f2448502dffa83600fc278444b816fc33fb796 100644 (file)
@@ -30,13 +30,19 @@ int c_simple_http_internal_get_string_part_full_size(void *data, void *ud) {
   return 0;
 }
 
-int c_simple_http_internal_combine_string_parts_from_list(void *data, void *ud) {
+int c_simple_http_internal_combine_string_parts_from_list(void *data,
+                                                          void *ud) {
   C_SIMPLE_HTTP_String_Part *part = data;
   void **ptrs = ud;
   char *buf = ptrs[0];
   size_t *current_count = ptrs[1];
   const size_t *total_count = ptrs[2];
 
+  if (!part->buf || part->size == 0) {
+    // Empty string part, just continue.
+    return 0;
+  }
+
   if (*current_count + part->size - 1 > *total_count) {
     fprintf(stderr, "ERROR Invalid state combining string parts!\n");
     return 1;
@@ -49,12 +55,21 @@ int c_simple_http_internal_combine_string_parts_from_list(void *data, void *ud)
   return 0;
 }
 
+void c_simple_http_cleanup_attr_string_part(C_SIMPLE_HTTP_String_Part **part) {
+  if (part && *part) {
+    if ((*part)->buf) {
+      free((*part)->buf);
+    }
+    free(*part);
+  }
+  *part = NULL;
+}
+
 void c_simple_http_cleanup_string_part(void *data) {
   C_SIMPLE_HTTP_String_Part *part = data;
   if (part) {
     if (part->buf) {
       free(part->buf);
-      part->buf = NULL;
     }
     free(part);
   }
index a53a94734a3c2b6dbef1dbd9a2094886549236d7..6c4554c2157d3a2e61b1d0cfdfcf129d663f2b7d 100644 (file)
@@ -29,6 +29,8 @@ typedef struct C_SIMPLE_HTTP_String_Part {
   size_t extra;
 } C_SIMPLE_HTTP_String_Part;
 
+void c_simple_http_cleanup_attr_string_part(C_SIMPLE_HTTP_String_Part **);
+
 /// Assumes "data" is a C_SIMPLE_HTTP_String_Part, "data" was malloced, and
 /// "data->buf" was malloced.
 void c_simple_http_cleanup_string_part(void *data);
index 2a47a3d5cf48c0cddf6d3a114756d121013a50ec..b6510181d0dbb8db8bead1e0ce5cd8e7d5ba0a5f 100644 (file)
 #include <SimpleArchiver/src/data_structures/linked_list.h>
 #include <SimpleArchiver/src/helpers.h>
 
-typedef struct C_SIMPLE_HTTP_INTERNAL_Template_Node {
-  char *html;
-  size_t html_size;
-  union {
-    size_t orig_end_idx;
-    size_t html_capacity;
-  };
-} C_SIMPLE_HTTP_INTERNAL_Template_Node;
-
-void c_simple_http_internal_free_template_node(void *data) {
-  C_SIMPLE_HTTP_INTERNAL_Template_Node *node = data;
-  if (node) {
-    if (node->html) {
-      free(node->html);
-    }
-    free(node);
-  }
-}
-
-void c_simple_http_internal_cleanup_template_node(
-    C_SIMPLE_HTTP_INTERNAL_Template_Node **node) {
-  if (node && *node) {
-    c_simple_http_internal_free_template_node(*node);
-    *node = NULL;
-  }
-}
-
-int c_simple_http_internal_get_final_size_fn(void *data, void *ud) {
-  size_t *final_size = ud;
-  C_SIMPLE_HTTP_INTERNAL_Template_Node *node = data;
-  *final_size += node->html_size;
-  return 0;
-}
-
-int c_simple_http_internal_fill_buf_fn(void *data, void *ud) {
-  C_SIMPLE_HTTP_INTERNAL_Template_Node *node = data;
-  C_SIMPLE_HTTP_INTERNAL_Template_Node *to_fill = ud;
-  if (to_fill->html_capacity < to_fill->html_size + node->html_size) {
-    return 1;
-  }
-  memcpy(
-    to_fill->html + to_fill->html_size,
-    node->html,
-    node->html_size);
-  to_fill->html_size += node->html_size;
-  return 0;
-}
+// Local includes.
+#include "helpers.h"
 
 /// Returns 0 if "c_string" ends with "_FILE".
 int c_simple_http_internal_ends_with_FILE(const char *c_string) {
@@ -162,13 +117,12 @@ char *c_simple_http_path_to_generated(
 
   // At this point, html_buf contains the raw HTML as a C-string.
   __attribute__((cleanup(simple_archiver_list_free)))
-  SDArchiverLinkedList *template_html_list = simple_archiver_list_init();
+  SDArchiverLinkedList *string_part_list = simple_archiver_list_init();
 
   size_t idx = 0;
   size_t last_template_idx = 0;
 
-  __attribute__((cleanup(c_simple_http_internal_cleanup_template_node)))
-  C_SIMPLE_HTTP_INTERNAL_Template_Node *template_node = NULL;
+  C_SIMPLE_HTTP_String_Part string_part;
 
   size_t delimeter_count = 0;
 
@@ -184,22 +138,23 @@ char *c_simple_http_path_to_generated(
         if (delimeter_count >= 3) {
           delimeter_count = 0;
           state |= 1;
-          if (template_html_list->count != 0) {
-            C_SIMPLE_HTTP_INTERNAL_Template_Node *last_node =
-              template_html_list->tail->prev->data;
-            last_template_idx = last_node->orig_end_idx;
+          if (string_part_list->count != 0) {
+            C_SIMPLE_HTTP_String_Part *last_part =
+              string_part_list->tail->prev->data;
+            last_template_idx = last_part->extra;
           }
-          template_node = malloc(sizeof(C_SIMPLE_HTTP_INTERNAL_Template_Node));
-          template_node->html_size = idx - last_template_idx - 2;
-          template_node->html = malloc(template_node->html_size);
+          string_part.size = idx - last_template_idx - 1;
+          string_part.buf = malloc(string_part.size);
           memcpy(
-            template_node->html,
+            string_part.buf,
             html_buf + last_template_idx,
-            template_node->html_size);
-          template_node->orig_end_idx = idx + 1;
-          simple_archiver_list_add(template_html_list, template_node,
-            c_simple_http_internal_free_template_node);
-          template_node = NULL;
+            string_part.size);
+          string_part.buf[string_part.size - 1] = 0;
+          string_part.extra = idx + 1;
+          c_simple_http_add_string_part(string_part_list,
+                                        string_part.buf,
+                                        string_part.extra);
+          free(string_part.buf);
         }
       } else {
         delimeter_count = 0;
@@ -212,14 +167,14 @@ char *c_simple_http_path_to_generated(
         if (delimeter_count >= 3) {
           delimeter_count = 0;
           state &= 0xFFFFFFFE;
-          C_SIMPLE_HTTP_INTERNAL_Template_Node *last_node =
-            template_html_list->tail->prev->data;
-          size_t var_size = idx - 2 - last_node->orig_end_idx;
+          C_SIMPLE_HTTP_String_Part *last_part =
+            string_part_list->tail->prev->data;
+          size_t var_size = idx - 2 - last_part->extra;
           __attribute__((cleanup(simple_archiver_helper_cleanup_c_string)))
           char *var = malloc(var_size + 1);
           memcpy(
             var,
-            html_buf + last_node->orig_end_idx,
+            html_buf + last_part->extra,
             var_size);
           var[var_size] = 0;
           const char *value_c_str =
@@ -252,14 +207,12 @@ char *c_simple_http_path_to_generated(
                         value_c_str);
                 return NULL;
               }
-              template_node =
-                malloc(sizeof(C_SIMPLE_HTTP_INTERNAL_Template_Node));
-              template_node->html_size = (size_t)file_size;
-              template_node->html = malloc(template_node->html_size);
-              template_node->orig_end_idx = idx + 1;
+              string_part.size = (size_t)file_size + 1;
+              string_part.buf = malloc(string_part.size);
+              string_part.extra = idx + 1;
 
-              if (fread(template_node->html,
-                        template_node->html_size,
+              if (fread(string_part.buf,
+                        string_part.size - 1,
                         1,
                         f)
                     != 1) {
@@ -267,6 +220,7 @@ char *c_simple_http_path_to_generated(
                         value_c_str);
                 return NULL;
               }
+              string_part.buf[string_part.size - 1] = 0;
               if (files_list_out) {
                 char *variable_filename = malloc(strlen(value_c_str) + 1);
                 strcpy(variable_filename, value_c_str);
@@ -275,24 +229,21 @@ char *c_simple_http_path_to_generated(
               }
             } else {
               // Variable data is "value_c_str".
-              template_node =
-                malloc(sizeof(C_SIMPLE_HTTP_INTERNAL_Template_Node));
-              size_t size = strlen(value_c_str);
-              template_node->html = malloc(size);
-              memcpy(template_node->html, value_c_str, size);
-              template_node->html_size = size;
-              template_node->orig_end_idx = idx + 1;
+              string_part.size = strlen(value_c_str) + 1;
+              string_part.buf = malloc(string_part.size);
+              memcpy(string_part.buf, value_c_str, string_part.size);
+              string_part.buf[string_part.size - 1] = 0;
+              string_part.extra = idx + 1;
             }
           } else {
-            template_node =
-              malloc(sizeof(C_SIMPLE_HTTP_INTERNAL_Template_Node));
-            template_node->html = NULL;
-            template_node->html_size = 0;
-            template_node->orig_end_idx = idx + 1;
+            string_part.buf = NULL;
+            string_part.size = 0;
+            string_part.extra = idx + 1;
           }
-          simple_archiver_list_add(template_html_list, template_node,
-            c_simple_http_internal_free_template_node);
-          template_node = NULL;
+          c_simple_http_add_string_part(string_part_list,
+                                        string_part.buf,
+                                        string_part.extra);
+          free(string_part.buf);
         }
       } else {
         delimeter_count = 0;
@@ -300,48 +251,28 @@ char *c_simple_http_path_to_generated(
     }
   }
 
-  if (template_html_list->count != 0) {
-    C_SIMPLE_HTTP_INTERNAL_Template_Node *last_node =
-      template_html_list->tail->prev->data;
-    if (idx > last_node->orig_end_idx) {
-      template_node = malloc(sizeof(C_SIMPLE_HTTP_INTERNAL_Template_Node));
-      size_t size = idx - last_node->orig_end_idx;
-      template_node->html = malloc(size);
-      memcpy(template_node->html, html_buf + last_node->orig_end_idx, size);
-      template_node->html_size = size;
-      template_node->orig_end_idx = idx + 1;
-      simple_archiver_list_add(template_html_list, template_node,
-        c_simple_http_internal_free_template_node);
-      template_node = NULL;
+  if (string_part_list->count != 0) {
+    C_SIMPLE_HTTP_String_Part *last_part =
+      string_part_list->tail->prev->data;
+    if (idx > last_part->extra) {
+      string_part.size = idx - last_part->extra + 1;
+      string_part.buf = malloc(string_part.size);
+      memcpy(string_part.buf, html_buf + last_part->extra, string_part.size);
+      string_part.buf[string_part.size - 1] = 0;
+      string_part.extra = idx + 1;
+      c_simple_http_add_string_part(string_part_list,
+                                    string_part.buf,
+                                    string_part.extra);
+      free(string_part.buf);
 
-      last_node = template_html_list->tail->prev->data;
+      last_part = string_part_list->tail->prev->data;
     }
-    size_t final_size = 0;
-    simple_archiver_list_get(
-      template_html_list,
-      c_simple_http_internal_get_final_size_fn,
-      &final_size);
-    if (final_size == 0) {
-      fprintf(stderr, "ERROR final_size calculated as ZERO from templates!\n");
-      return NULL;
-    }
-    C_SIMPLE_HTTP_INTERNAL_Template_Node to_fill;
-    to_fill.html = malloc(final_size + 1);
-    to_fill.html_size = 0;
-    to_fill.html_capacity = final_size;
-    if (simple_archiver_list_get(
-        template_html_list,
-        c_simple_http_internal_fill_buf_fn,
-        &to_fill) != NULL) {
-      fprintf(stderr, "ERROR internal issue processing final html buffer!\n");
-      free(to_fill.html);
-      return NULL;
-    }
-    to_fill.html[final_size] = 0;
+
+    char *combined_buf = c_simple_http_combine_string_parts(string_part_list);
     if (output_buf_size) {
-      *output_buf_size = final_size;
+      *output_buf_size = strlen(combined_buf);
     }
-    return to_fill.html;
+    return combined_buf;
   } else {
     // Prevent cleanup fn from "free"ing html_buf and return it verbatim.
     char *buf = html_buf;