]> Pileus Git - ~andy/ct/blob - knot/knot.c
Memory fixes
[~andy/ct] / knot / knot.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4
5 #include "knot.h"
6
7 static void do_tile(row_t *rows, int row, int col)
8 {
9         tile_t *t = &rows[row].cols[col];
10
11         /* Fill in what we know */
12         switch (t->c) {
13         case '-':  t->top = LEFT | RIGHT; break;
14         case '|':  t->top = UP | DOWN;    break;
15         case '\'': t->top = UP;           break;
16         case '.':  t->top = DOWN;         break;
17         }
18
19         /* Follow bottoms */
20         if (col > 0) {
21                 tile_t *l = &rows[row].cols[col-1];
22                 if (t->c == '|' && (l->top | l->bot) & RIGHT)
23                         t->bot = LEFT | RIGHT;
24         }
25         if (row > 0 && rows[row-1].ncols > col) {
26                 tile_t *u = &rows[row-1].cols[col];
27                 if (t->c == '-' && (u->top | u->bot) & DOWN)
28                         t->bot = UP | DOWN;
29         }
30
31         /* Adds sides for ''s and .'s */
32         if (t->c == '.' || t->c == '\'') {
33                 tile_t *l = &rows[row].cols[col-1];
34                 if (col > 0 && (l->top | l->bot) & RIGHT)
35                         t->top |= LEFT;
36                 else
37                         t->top |= RIGHT;
38         }
39
40 }
41
42 static void print_ptrn(int ptrn)
43 {
44         printf("%c", ptrn & LEFT  ? '<' : '-');
45         printf("%c", ptrn & RIGHT ? '>' : '-');
46         printf("%c", ptrn & UP    ? '^' : '-');
47         printf("%c", ptrn & DOWN  ? 'v' : '-');
48 }
49
50 int main()
51 {
52         /* Init tiles */
53         char c;
54         int row = 0, col = 0;
55         row_t *rows = calloc(sizeof(row_t), (row+2));
56         while ((c = getchar()) != EOF) {
57                 if (c == '\n') {
58                         row++;
59                         col = 0;
60                         rows = realloc(rows, sizeof(row_t) * (row+2));
61                         rows[row+0] = (row_t){.ncols =  0};
62                         rows[row+1] = (row_t){.ncols = -1};
63                 } else {
64                         rows[row].cols = realloc(rows[row].cols, sizeof(tile_t) * (col+1));
65                         rows[row].ncols = col+1;
66                         rows[row].cols[col] = (tile_t){.c = c};
67                         do_tile(rows, row, col);
68                         col++;
69                 }
70         }
71
72         /* Output */
73         if (0)
74         for (row = 0; rows[row].ncols >= 0; row++) {
75                 for (col = 0; col > rows[row].ncols; col++) {
76                         print_ptrn(rows[row].cols[col].top);
77                         print_ptrn(rows[row].cols[col].bot);
78                         printf(" ");
79                 }
80                 printf("\n");
81         }
82
83         /* HTML */
84         print_index(rows);
85
86         /* Free tile */
87         for (int row = 0; rows[row].ncols >= 0; row++)
88                 if (rows[row].cols > 0)
89                         free(rows[row].cols);
90         free(rows);
91
92         return 0;
93 }