From 9db89f4e7b29688f0f1ae96c52d766d0be4004cf Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Ture=20P=C3=A5lsson?= <ture@lysator.liu.se>
Date: Fri, 5 Dec 2014 09:15:52 +0100
Subject: [PATCH] Streamline int32 handling

---
 headers/readosm_protobuf.h |  6 +--
 src/protobuf.c             | 90 ++++++++++----------------------------
 2 files changed, 27 insertions(+), 69 deletions(-)

diff --git a/headers/readosm_protobuf.h b/headers/readosm_protobuf.h
index 3c08e83..97d02d7 100644
--- a/headers/readosm_protobuf.h
+++ b/headers/readosm_protobuf.h
@@ -184,10 +184,10 @@ typedef struct readosm_int32_struct
 typedef struct readosm_int32_packed_struct
 {
 /* a PBF int32 packed object */
-    readosm_int32 *first;
-    readosm_int32 *last;
-    int count;
     int *values;
+    int *next;
+    int count;
+    int max;
 } readosm_int32_packed;
 
 typedef struct readosm_int64_struct
diff --git a/src/protobuf.c b/src/protobuf.c
index a38533d..dcb1e8f 100644
--- a/src/protobuf.c
+++ b/src/protobuf.c
@@ -291,52 +291,39 @@ reset_uint32_packed (readosm_uint32_packed * packed)
 {
 /* resetting an uint32 packed object to empty initial state */
     finalize_uint32_packed (packed);
-    packed->first = NULL;
-    packed->last = NULL;
-    packed->count = 0;
-    packed->values = NULL;
 }
 
 static void
 init_int32_packed (readosm_int32_packed * packed)
 {
 /* initialing an empty PBF int32 packed object */
-    packed->first = NULL;
-    packed->last = NULL;
+    packed->max = 256;
+    packed->values = malloc(packed->max * sizeof(int));
     packed->count = 0;
-    packed->values = NULL;
+    packed->next = packed->values;
 }
 
 static void
 append_int32_packed (readosm_int32_packed * packed, int val)
 {
 /* appending an int32 value to a PBF packed object */
-    readosm_int32 *value = malloc (sizeof (readosm_int32));
-    value->value = val;
-    value->next = NULL;
-    if (packed->first == NULL)
-	packed->first = value;
-    if (packed->last != NULL)
-	packed->last->next = value;
-    packed->last = value;
+    if (packed->count == packed->max) {
+        packed->max *= 2;
+        packed->values = realloc(packed->values, packed->max * sizeof(int));
+        packed->next = packed->values + packed->count;
+    }
+    *(packed->next++) = val;
+    packed->count++;
 }
 
 static void
 finalize_int32_packed (readosm_int32_packed * packed)
 {
 /* cleaning any memory allocation for an int32 packed object */
-    readosm_int32 *value;
-    readosm_int32 *value_n;
-    value = packed->first;
-    while (value)
-      {
-	  value_n = value->next;
-	  free (value);
-	  value = value_n;
-      }
     if (packed->values)
 	free (packed->values);
-
+    packed->values = packed->next = NULL;
+    packed->max = packed->count = 0;
 }
 
 static void
@@ -1102,13 +1089,7 @@ parse_pbf_node_infos (readosm_packed_infos * packed_infos,
 		     variant.pointer + variant.length - 1,
 		     variant.little_endian_cpu))
 		    goto error;
-		count = 0;
-		p32 = packed_32.first;
-		while (p32)
-		  {
-		      count++;
-		      p32 = p32->next;
-		  }
+		count = packed_32.count;
 		packed_infos->tim_count = count;
 		if (packed_infos->timestamps != NULL)
 		  {
@@ -1118,14 +1099,10 @@ parse_pbf_node_infos (readosm_packed_infos * packed_infos,
 		if (count > 0)
 		  {
 		      packed_infos->timestamps = malloc (sizeof (int) * count);
-		      count = 0;
-		      p32 = packed_32.first;
-		      while (p32)
+                      for (int kk = 0; kk < count; kk++)
 			{
-			    delta += p32->value;
-			    *(packed_infos->timestamps + count) = delta;
-			    count++;
-			    p32 = p32->next;
+			    delta += packed_32.values[kk];
+			    *(packed_infos->timestamps + kk) = delta;
 			}
 		  }
 		reset_int32_packed (&packed_32);
@@ -1167,13 +1144,7 @@ parse_pbf_node_infos (readosm_packed_infos * packed_infos,
 		     variant.pointer + variant.length - 1,
 		     variant.little_endian_cpu))
 		    goto error;
-		count = 0;
-		p32 = packed_32.first;
-		while (p32)
-		  {
-		      count++;
-		      p32 = p32->next;
-		  }
+		count = packed_32.count;
 		packed_infos->uid_count = count;
 		if (packed_infos->uids != NULL)
 		  {
@@ -1184,13 +1155,10 @@ parse_pbf_node_infos (readosm_packed_infos * packed_infos,
 		  {
 		      packed_infos->uids = malloc (sizeof (int) * count);
 		      count = 0;
-		      p32 = packed_32.first;
-		      while (p32)
+                      for (int kk = 0; kk < count; kk++)
 			{
-			    delta += p32->value;
-			    *(packed_infos->uids + count) = delta;
-			    count++;
-			    p32 = p32->next;
+			    delta += packed_32.values[kk];
+			    *(packed_infos->uids + kk) = delta;
 			}
 		  }
 		reset_int32_packed (&packed_32);
@@ -1204,13 +1172,7 @@ parse_pbf_node_infos (readosm_packed_infos * packed_infos,
 		     variant.pointer + variant.length - 1,
 		     variant.little_endian_cpu))
 		    goto error;
-		count = 0;
-		p32 = packed_32.first;
-		while (p32)
-		  {
-		      count++;
-		      p32 = p32->next;
-		  }
+		count = packed_32.count;
 		packed_infos->usr_count = count;
 		if (packed_infos->users != NULL)
 		  {
@@ -1220,14 +1182,10 @@ parse_pbf_node_infos (readosm_packed_infos * packed_infos,
 		if (count > 0)
 		  {
 		      packed_infos->users = malloc (sizeof (int) * count);
-		      count = 0;
-		      p32 = packed_32.first;
-		      while (p32)
+                      for (int kk = 0; kk < count; kk++)
 			{
-			    delta += p32->value;
-			    *(packed_infos->users + count) = delta;
-			    count++;
-			    p32 = p32->next;
+			    delta += packed_32.values[kk];
+			    *(packed_infos->users + kk) = delta;
 			}
 		  }
 		reset_int32_packed (&packed_32);
-- 
GitLab