============================================
Number literals
============================================

int a = 0xAC00;
int b = 0.123;
int c = 0b1010001;

---

(translation_unit
  (declaration (identifier) (init_declarator (identifier) (number_literal)))
  (declaration (identifier) (init_declarator (identifier) (number_literal)))
  (declaration (identifier) (init_declarator (identifier) (number_literal))))

============================================
Identifiers
============================================

int main() {
  _abc;
  d_EG123;
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (identifier))
      (expression_statement (identifier)))))

============================================
Function calls
============================================

int main() {
  printf("hi! %d\n", x);
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (call_expression (identifier) (string_literal) (identifier))))))

============================================
Character literals
============================================

int main() {
  'a';
  '\0';
  '\t';
  '\'';
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (char_literal))
      (expression_statement (char_literal))
      (expression_statement (char_literal))
      (expression_statement (char_literal)))))

============================================
Field access
============================================

int main() {
  s.data1;
  p->data2;
  q[data3];
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (field_expression (identifier) (identifier)))
      (expression_statement (field_expression (identifier) (identifier)))
      (expression_statement (subscript_expression (identifier) (identifier))))))

============================================
Boolean operators
============================================

int main() {
  !x || !y && !z;
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (logical_expression
        (logical_expression (identifier))
        (logical_expression
          (logical_expression (identifier))
          (logical_expression (identifier))))))))

============================================
Math operators
============================================

int main() {
  -a / b + c * -d;
  a++ - ++b + c-- + --d;
  }

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (math_expression
        (math_expression
          (math_expression (identifier))
          (identifier))
        (math_expression
          (identifier)
          (math_expression (identifier)))))
      (expression_statement
        (math_expression
          (math_expression
            (math_expression
              (math_expression (identifier))
              (math_expression (identifier)))
            (math_expression (identifier)))
          (math_expression (identifier)))))))

============================================
Assignments
============================================

int main() {
  static int a = 1;
  b = *c = 2;
  d.e = 3;
  f->g = 4;
  h[i] = j;
  k += l;
  m -= o;
  n *= p;
  q /= r;
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (declaration (storage_class_specifier) (identifier) (init_declarator (identifier) (number_literal)))
      (expression_statement (assignment_expression (identifier) (assignment_expression (pointer_expression (identifier)) (number_literal))))
      (expression_statement (assignment_expression (field_expression (identifier) (identifier)) (number_literal)))
      (expression_statement (assignment_expression (field_expression (identifier) (identifier)) (number_literal)))
      (expression_statement (assignment_expression (subscript_expression (identifier) (identifier)) (identifier)))
      (expression_statement (assignment_expression (identifier) (identifier)))
      (expression_statement (assignment_expression (identifier) (identifier)))
      (expression_statement (assignment_expression (identifier) (identifier)))
      (expression_statement (assignment_expression (identifier) (identifier))))))

============================================
Pointer operations
============================================

int main() {
  doSomething(&x, *x);
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (call_expression (identifier)
        (pointer_expression (identifier))
        (pointer_expression (identifier)))))))

============================================
Type-casts
============================================

int main() {
  x = (const SomeType *)thing;
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (assignment_expression
        (identifier)
        (cast_expression
          (type_name (type_qualifier) (identifier) (abstract_pointer_declarator))
          (identifier)))))))

============================================
Sizeof expressions
============================================

int main() {
  sizeof x.a;
  sizeof(x.a);
  sizeof(const char **);
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (sizeof_expression (field_expression (identifier) (identifier))))
      (expression_statement (sizeof_expression (field_expression (identifier) (identifier))))
      (expression_statement (sizeof_expression
        (type_name (type_qualifier) (identifier) (abstract_pointer_declarator (abstract_pointer_declarator))))))))

============================================
Compound literals
============================================

int main() {
  x = (SomeType) { .f1 = 5, .f2 = 6 };
  y = (struct SomeStruct) { 7, 8 };
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (assignment_expression
        (identifier)
        (compound_literal_expression
          (type_name (identifier))
          (initializer_list
            (designator (identifier)) (number_literal)
            (designator (identifier)) (number_literal)))))
      (expression_statement (assignment_expression
        (identifier)
        (compound_literal_expression
          (type_name (struct_specifier (identifier)))
          (initializer_list
            (number_literal)
            (number_literal))))))))

============================================
Compound literals with trailing commas
============================================

int main() {
  x = (SomeType) { .f1 = 5, .f2 = 6, };
  y = (struct SomeStruct) { 7, 8, };
}

---

(translation_unit
  (function_definition
    (identifier)
    (function_declarator (identifier))
    (compound_statement
      (expression_statement (assignment_expression
        (identifier)
        (compound_literal_expression
          (type_name (identifier))
          (initializer_list
            (designator (identifier)) (number_literal)
            (designator (identifier)) (number_literal)))))
      (expression_statement (assignment_expression
        (identifier)
        (compound_literal_expression
          (type_name (struct_specifier (identifier)))
          (initializer_list
            (number_literal)
            (number_literal))))))))
