#include <perms.h>

//          Edinburgh IMP77 Compiler - Version 8.4
//
//     1  %begin

int main(int argc, char **argv) { /*%begin*/
  _imp_initialise(argc, argv);

  //     2    %string (10) %fn ten lit

  _imp_string10 TENLIT(void) {
    //     3      %result = "fives"

    return *(_imp_string10 *)/*?*/ _imp_str_literal_ptr("fives");

    //     4    %end

  } /* end of TENLIT */

  //     5
  //     6    %string (10) %fn ten var

  _imp_string10 TENVAR(void) {
    //     7      %string(7) seven = "four"

    _imp_string7 SEVEN;

    /* clang-format off */
_imp_strncpy(/*?*/&SEVEN, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = _imp_str_literal("four"); (void *)&tmp;}), /*max:*/7);

    /* clang-format on */

    //     8      %result = seven

    return *(_imp_string10 *)/*?*/ &SEVEN;

    //     9    %end

  } /* end of TENVAR */

  //    10
  //    11    %string (255) %fn big lit

  _imp_string255 BIGLIT(void) {
    //    12      %result = "a longer string"

    return *(_imp_string255 *)/*?*/ _imp_str_literal_ptr("a longer string");

    //    13    %end

  } /* end of BIGLIT */

  //    14
  //    15    %string (255) %fn big

  _imp_string255 BIG(void) {
    //    16      %string (15) medium

    _imp_string15 MEDIUM;

    //    17      medium = "a longer string"


    /* clang-format off */
_imp_strncpy(/*?*/&MEDIUM, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = _imp_str_literal("a longer string"); (void *)&tmp;}), /*max:*/15);

    /* clang-format on */

    //    18      %result = medium

    return *(_imp_string255 *)/*?*/ &MEDIUM;

    //    19    %end

  } /* end of BIG */

  //    20
  //    21    %string (3) short

  _imp_string3 SHORT;

  //    22    %string (50) medium

  _imp_string50 MEDIUM;

  //    23    %string (255) huge

  _imp_string255 HUGE;
  auto void DO63(_imp_string63 S);

  auto void DO255(_imp_string255 S);

  //    24
  //    25    %routinespec do63(%string (63) S)
  //    26    %routinespec do255(%string (255) S)
  //    27
  //    28    %routine do15(%string (15) S)

  void DO15(_imp_string15 S) {
    //    29      do63(S) %if 0=1

    if (0 != 1) goto L_0001;
    DO63(
        /* clang-format off */
*({  __typeof__(_imp_string15) tmp = S/*q*/;  (_imp_string63 *)&tmp;  })
        /* clang-format on */
    );
  L_0001:;

  //    30      do255(S) %if 0=1

    if (0 != 1) goto L_0002;
    DO255(
        /* clang-format off */
*({  __typeof__(_imp_string15) tmp = S/*q*/;  (_imp_string255 *)&tmp;  })
        /* clang-format on */
    );
  L_0002:;

  //    31    %end

    return;
  } /* end of DO15 */

  //    32
  //    33    %routine do63(%string (63) S)

  void DO63(_imp_string63 S) {
    //    34      do15(S)

    DO15(
        /* clang-format off */
*({  __typeof__(_imp_string63) tmp = S/*q*/;  (_imp_string15 *)&tmp;  })
        /* clang-format on */
    );

    //    35      do255(S) %if 0=1

    if (0 != 1) goto L_0003;
    DO255(
        /* clang-format off */
*({  __typeof__(_imp_string63) tmp = S/*q*/;  (_imp_string255 *)&tmp;  })
        /* clang-format on */
    );
  L_0003:;

  //    36    %end

    return;
  } /* end of DO63 */

  //    37
  //    38    %routine do255(%string (255) S)

  void DO255(_imp_string255 S) {
    //    39      do15(S)

    DO15(
        /* clang-format off */
*({  __typeof__(_imp_string255) tmp = S/*q*/;  (_imp_string15 *)&tmp;  })
        /* clang-format on */
    );

    //    40      do63(S)

    DO63(
        /* clang-format off */
*({  __typeof__(_imp_string255) tmp = S/*q*/;  (_imp_string63 *)&tmp;  })
        /* clang-format on */
    );

    //    41    %end

    return;
  } /* end of DO255 */

  //    42
  //    43    do15(ten lit)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string10) tmp = TENLIT()/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    44    do15(ten var)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string10) tmp = TENVAR()/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    45    do15(big lit)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = BIGLIT()/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    46    do15(big)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = BIG()/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    47
  //    48    do15(short)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string3) tmp = SHORT/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    49    do15(medium)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string50) tmp = MEDIUM/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    50    do15(huge)

  DO15(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = HUGE/*q*/;  (_imp_string15 *)&tmp;  })
      /* clang-format on */
  );

  //    51
  //    52    do15("123")

  DO15(_imp_str_literal_size(15, "123"));

  //    53    ! This line *could* have been faulted by Imp77 pass1 but wasn't, however C caught it...
  //    54    ! (on the plus side, my code will catch it at runtime)
  //    55    do15("a lot longer than fifteen characters I think")

  DO15(_imp_str_literal_size(15, "a lot longer than fifteen characters I think"));

  //    56
  //    57    do63(short)

  DO63(
      /* clang-format off */
*({  __typeof__(_imp_string3) tmp = SHORT/*q*/;  (_imp_string63 *)&tmp;  })
      /* clang-format on */
  );

  //    58    do63(medium)

  DO63(
      /* clang-format off */
*({  __typeof__(_imp_string50) tmp = MEDIUM/*q*/;  (_imp_string63 *)&tmp;  })
      /* clang-format on */
  );

  //    59    do63(huge)

  DO63(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = HUGE/*q*/;  (_imp_string63 *)&tmp;  })
      /* clang-format on */
  );

  //    60
  //    61    do63("123")

  DO63(_imp_str_literal_size(63, "123"));

  //    62    do63("a lot longer than fifteen characters I think")

  DO63(_imp_str_literal_size(63, "a lot longer than fifteen characters I think"));

  //    63
  //    64    do255(short)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string3) tmp = SHORT/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    65    do255(medium)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string50) tmp = MEDIUM/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    66    do255(huge)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = HUGE/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    67
  //    68    do255(ten lit)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string10) tmp = TENLIT()/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    69    do255(ten var)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string10) tmp = TENVAR()/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    70    do255(big lit)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = BIGLIT()/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    71    do255(big)

  DO255(
      /* clang-format off */
*({  __typeof__(_imp_string255) tmp = BIG()/*q*/;  (_imp_string255 *)&tmp;  })
      /* clang-format on */
  );

  //    72
  //    73    do255("123")

  DO255(_imp_str_literal("123"));

  //    74    do255("a lot longer than fifteen characters I think")

  DO255(_imp_str_literal("a lot longer than fifteen characters I think"));

  //    75
  //    76    huge = "123"


  /* clang-format off */
_imp_strncpy(/*?*/&HUGE, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = _imp_str_literal("123"); (void *)&tmp;}), /*max:*/255);

  /* clang-format on */

  //    77    huge = big


  /* clang-format off */
_imp_strncpy(/*?*/&HUGE, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = BIG(); (void *)&tmp;}), /*max:*/255);

  /* clang-format on */

  //    78    huge = big lit


  /* clang-format off */
_imp_strncpy(/*?*/&HUGE, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = BIGLIT(); (void *)&tmp;}), /*max:*/255);

  /* clang-format on */

  //    79    huge = ten var


  /* clang-format off */
_imp_strncpy(/*?*/&HUGE, ({__typeof__(_imp_string10) tmp;/*B*/ tmp = TENVAR(); (void *)&tmp;}), /*max:*/255);

  /* clang-format on */

  //    80    huge = ten lit


  /* clang-format off */
_imp_strncpy(/*?*/&HUGE, ({__typeof__(_imp_string10) tmp;/*B*/ tmp = TENLIT(); (void *)&tmp;}), /*max:*/255);

  /* clang-format on */

  //    81
  //    82    medium = "123"


  /* clang-format off */
_imp_strncpy(/*?*/&MEDIUM, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = _imp_str_literal("123"); (void *)&tmp;}), /*max:*/50);

  /* clang-format on */

  //    83    medium = big


  /* clang-format off */
_imp_strncpy(/*?*/&MEDIUM, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = BIG(); (void *)&tmp;}), /*max:*/50);

  /* clang-format on */

  //    84    medium = big lit


  /* clang-format off */
_imp_strncpy(/*?*/&MEDIUM, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = BIGLIT(); (void *)&tmp;}), /*max:*/50);

  /* clang-format on */

  //    85    medium = ten var


  /* clang-format off */
_imp_strncpy(/*?*/&MEDIUM, ({__typeof__(_imp_string10) tmp;/*B*/ tmp = TENVAR(); (void *)&tmp;}), /*max:*/50);

  /* clang-format on */

  //    86    medium = ten lit


  /* clang-format off */
_imp_strncpy(/*?*/&MEDIUM, ({__typeof__(_imp_string10) tmp;/*B*/ tmp = TENLIT(); (void *)&tmp;}), /*max:*/50);

  /* clang-format on */

  //    87
  //    88    short = "123"


  /* clang-format off */
_imp_strncpy(/*?*/&SHORT, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = _imp_str_literal("123"); (void *)&tmp;}), /*max:*/3);

  /* clang-format on */

  //    89  ! These should cause errors...
  //    90    short = big


  /* clang-format off */
_imp_strncpy(/*?*/&SHORT, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = BIG(); (void *)&tmp;}), /*max:*/3);

  /* clang-format on */

  //    91    short = big lit


  /* clang-format off */
_imp_strncpy(/*?*/&SHORT, ({__typeof__(_imp_string255) tmp;/*B*/ tmp = BIGLIT(); (void *)&tmp;}), /*max:*/3);

  /* clang-format on */

  //    92    short = ten var


  /* clang-format off */
_imp_strncpy(/*?*/&SHORT, ({__typeof__(_imp_string10) tmp;/*B*/ tmp = TENVAR(); (void *)&tmp;}), /*max:*/3);

  /* clang-format on */

  //    93    short = ten lit


  /* clang-format off */
_imp_strncpy(/*?*/&SHORT, ({__typeof__(_imp_string10) tmp;/*B*/ tmp = TENLIT(); (void *)&tmp;}), /*max:*/3);

  /* clang-format on */

  //    94
  //    95
  //    96  %endofprogram

  _imp_stop(0);
  return 0;
end_0:;
}