changeset 458:1c18c2377c24

suite_aggr: - bounds checking memory of struct return values, to spot overflow errors by dcCallStruct - added clearing of space aggregate data is written to, to be in line with other data which is cleared - some optimization
author Tassilo Philipp
date Sat, 29 Jan 2022 12:02:56 +0100
parents 90b1d927912a
children 8b6a39592f86
files test/suite_aggrs/globals.c test/suite_aggrs/globals.h test/suite_aggrs/main.c
diffstat 3 files changed, 25 insertions(+), 8 deletions(-) [+]
line wrap: on
line diff
--- a/test/suite_aggrs/globals.c	Fri Jan 28 14:11:21 2022 +0100
+++ b/test/suite_aggrs/globals.c	Sat Jan 29 12:02:56 2022 +0100
@@ -49,19 +49,22 @@
   }
 }
 
-static int calc_max_aggr_size()
+int get_max_aggr_size()
 {
-  int i, s = 0;
-  for(i=0; i<G_naggs; ++i)
-    if(G_agg_sizes[i] > s)
-      s = G_agg_sizes[i];
+  static int s = 0;
+  int i;
+  if(s == 0) {
+    for(i=0; i<G_naggs; ++i)
+      if(G_agg_sizes[i] > s)
+        s = G_agg_sizes[i];
+  }
   return s;
 }
 
 void init_test_data()
 {
   int i;
-  int maxaggrsize = calc_max_aggr_size();
+  int maxaggrsize = get_max_aggr_size();
 #define X(CH,T) V_##CH = (T*) malloc(sizeof(T)*(G_maxargs+1)); K_##CH = (T*) malloc(sizeof(T)*(G_maxargs+1));
 DEF_TYPES
 #undef X
@@ -84,7 +87,7 @@
 void clear_V()
 {
   static int aggr_init = 0;
-  int maxaggrsize = calc_max_aggr_size();
+  int maxaggrsize = get_max_aggr_size();
 
   int i;
   for(i=0;i<G_maxargs+1;++i) {
@@ -94,6 +97,7 @@
 DEF_TYPES
 #undef X
     V_a[i] = malloc(maxaggrsize+AGGR_MISALIGN);
+    memset(V_a[i], 0, maxaggrsize+AGGR_MISALIGN);
     V_a[i] = (char*)V_a[i]+AGGR_MISALIGN;
   }
   aggr_init = 1;
--- a/test/suite_aggrs/globals.h	Fri Jan 28 14:11:21 2022 +0100
+++ b/test/suite_aggrs/globals.h	Sat Jan 29 12:02:56 2022 +0100
@@ -46,3 +46,4 @@
 void deinit_test_data();
 void clear_V();
 
+int get_max_aggr_size();
--- a/test/suite_aggrs/main.c	Fri Jan 28 14:11:21 2022 +0100
+++ b/test/suite_aggrs/main.c	Sat Jan 29 12:02:56 2022 +0100
@@ -51,6 +51,7 @@
   char const * sig_args;
   char         rtype;
   DCstruct *   rtype_st = NULL;
+  int          rtype_size = 0;
   funptr       rtype_st_cmp = NULL;
   char         atype;
   int          pos = 0;
@@ -70,6 +71,7 @@
     rtype = *sig;
     sig += len;
 
+    rtype_size = G_agg_sizes[i];
     rtype_st_cmp = G_agg_cmpfuncs[i];
     rtype_st = ((DCstruct*(*)())G_agg_touchdcstfuncs[i])();
     dcBeginCallStruct(p, rtype_st);
@@ -121,7 +123,17 @@
     case 'f': s = (dcCallFloat   (p,t) == K_f[pos]) ; break;
     case 'd': s = (dcCallDouble  (p,t) == K_d[pos]) ; break;
     case '{': {
-      s = ((int(*)(const void*,const void*))rtype_st_cmp)(dcCallStruct(p,t,rtype_st, V_a[0]/*unused space for retval*/), K_a[pos]);
+      /* bound check memory adjacent to returned struct, to check for overflows by dcCallStruct */
+      long long* adj_ll = (get_max_aggr_size() - rtype_size) > sizeof(long long) ? (long long*)((char*)V_a[0] + rtype_size) : NULL;
+      if(adj_ll)
+        *adj_ll = 0x0123456789abcdef;
+
+      s = ((int(*)(const void*,const void*))rtype_st_cmp)(dcCallStruct(p, t, rtype_st, V_a[0]), K_a[pos]);
+
+      if(*adj_ll != 0x0123456789abcdef) {
+        printf("writing rval overflowed into adjacent memory;");
+        return 0;
+      }
       break;
     }
     default: printf("unknown rtype '%c'", rtype); return 0;