Skip to content

[CN-Exec] Struct initializer issues #925

@ZippeyKeys12

Description

@ZippeyKeys12

Macros get confused with commas in struct initializers, which can be fixed with CN_IGNORE_COMMA, but it just fails then.

This limits user's abilities to reproduce failing inputs when testing.

List reverse example
struct int_list {
  int head;
  struct int_list *tail;
};

/*@
datatype seq {
  Seq_Nil {},
  Seq_Cons {i32 head, datatype seq tail}
}
predicate (datatype seq) IntList(pointer p) {
  if (is_null(p)) {
    return Seq_Nil{};
  } else {
    take H = Owned<struct int_list>(p);
    take tl = IntList(H.tail);
    return (Seq_Cons { head: H.head, tail: tl });
  }
}
function [rec] (datatype seq) append(datatype seq xs, datatype seq ys) {
  match xs {
    Seq_Nil {} => {
      ys
    }
    Seq_Cons {head : h, tail : zs}  => {
      Seq_Cons {head: h, tail: append(zs, ys)}
    }
  }
}
function [rec] (datatype seq) snoc(datatype seq xs, i32 y) {
  match xs {
    Seq_Nil {} => {
      Seq_Cons {head: y, tail: Seq_Nil{}}
    }
    Seq_Cons {head: x, tail: zs}  => {
      Seq_Cons{head: x, tail: snoc (zs, y)}
    }
  }
}
function [rec] (datatype seq) rev(datatype seq xs) {
  match xs {
    Seq_Nil {} => {
      Seq_Nil {}
    }
    Seq_Cons {head : h, tail : zs}  => {
      snoc (rev(zs), h)
    }
  }
}
@*/

struct int_list *IntList_rev_aux(struct int_list *xs, struct int_list *ys)
/*@ requires take L1 = IntList(xs); @*/
/*@ requires take L2 = IntList(ys); @*/
/*@ ensures take R = IntList(return); @*/
/*@ ensures R == append(rev(L2), L1); @*/
{
  if (ys == 0) {
    return xs;
  } else {
    struct int_list *tmp = ys->tail;
    ys->head = -1;
    ys->tail = xs;
    return IntList_rev_aux(ys, tmp);
  }
}

struct int_list *IntList_rev(struct int_list *xs)
/*@ requires take L1 = IntList(xs); @*/
/*@ ensures take L1_rev = IntList(return); @*/
/*@ ensures L1_rev == rev(L1); @*/
{
  return IntList_rev_aux(0, xs);
}

void *cn_malloc(unsigned long);

int main() {
  struct int_list *ys = cn_malloc(sizeof(struct int_list));
  *ys = (struct int_list){.head = 10, .tail = 0};
  struct int_list *xs = cn_malloc(sizeof(struct int_list));
  *xs = (struct int_list){.head = 7, .tail = ys};
  IntList_rev(xs);

  return 0;
}

Metadata

Metadata

Assignees

Labels

CN spec testingCN-execRelated to CN executable spec generation, called using `cn instrument`blockingbugSomething isn't workingcn

Type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions