1 /*
2 * enigma/memory.c - memory management routines.
3 *
4 * Copyright 2000 Simon Tatham. All rights reserved.
5 *
6 * Enigma is licensed under the MIT licence. See the file LICENCE for
7 * details.
8 *
9 * - we are all amf -
10 */
11
12 #include <stdio.h>
13 #include <stdlib.h>
14 #include <assert.h>
15 #include <string.h>
16
17 #include "enigma.h"
18
smalloc(size_t size)19 void *smalloc(size_t size) {
20 void *p = malloc(size);
21 if (!p)
22 fatal("Out of memory");
23 return p;
24 }
25
srealloc(void * q,size_t size)26 void *srealloc(void *q, size_t size) {
27 void *p = realloc(q, size);
28 if (!p)
29 fatal("Out of memory");
30 return p;
31 }
32
sfree(void * q)33 void sfree(void *q) {
34 if (q)
35 free(q);
36 }
37
dupstr(char * str)38 char *dupstr(char *str) {
39 char *p = (char *)smalloc(1+strlen(str));
40 strcpy(p, str);
41 return p;
42 }
43
44 #define mknew(type) ( (type *)smalloc(sizeof(type)) )
45 #define mknewn(type, n) ( (type *)smalloc(sizeof(type) * n) )
46 #define renewn(p, type, n) ( (type *)srealloc(p, sizeof(type) * n) )
47
gamestate_new(int width,int height,int flags)48 gamestate *gamestate_new(int width, int height, int flags) {
49 gamestate *p;
50
51 p = mknew(gamestate);
52 p->leveldata = mknewn(char, width * height);
53 p->width = width;
54 p->height = height;
55 p->flags = flags;
56 p->sequence = NULL;
57 p->sequence_size = 0;
58
59 return p;
60 }
61
gamestate_copy(gamestate * state)62 gamestate *gamestate_copy(gamestate *state) {
63 gamestate *ret;
64
65 ret = gamestate_new(state->width, state->height, state->flags);
66 ret->status = state->status;
67 memcpy(ret->leveldata, state->leveldata, ret->width * ret->height);
68 ret->player_x = state->player_x;
69 ret->player_y = state->player_y;
70 ret->gold_got = state->gold_got;
71 ret->gold_total = state->gold_total;
72 ret->levnum = state->levnum;
73 ret->title = state->title;
74 ret->movenum = state->movenum;
75 ret->sequence = smalloc(state->sequence_size);
76 memcpy(ret->sequence, state->sequence, state->movenum);
77 ret->sequence_size = state->sequence_size;
78
79 return ret;
80 }
81
gamestate_free(gamestate * p)82 void gamestate_free(gamestate *p) {
83 if (p) {
84 if (p->leveldata) free(p->leveldata);
85 if (p->sequence) free(p->sequence);
86 free(p);
87 }
88 }
89
level_new(void)90 level *level_new(void) {
91 level *p;
92
93 p = mknew(level);
94 p->leveldata = NULL;
95
96 return p;
97 }
98
level_setsize(level * p,int width,int height)99 void level_setsize(level *p, int width, int height) {
100 assert(p != NULL);
101 if (p) {
102 p->leveldata = mknewn(char, width * height);
103 p->width = width;
104 p->height = height;
105 }
106 }
107
level_free(level * p)108 void level_free(level *p) {
109 if (p) {
110 if (p->leveldata) free(p->leveldata);
111 free(p);
112 }
113 }
114
levelset_new(void)115 levelset *levelset_new(void) {
116 levelset *p;
117
118 p = mknew(levelset);
119 p->levels = NULL;
120 p->nlevels = 0;
121
122 return p;
123 }
124
levelset_nlevels(levelset * p,int n)125 void levelset_nlevels(levelset *p, int n) {
126 p->levels = renewn(p->levels, level *, n);
127 while (p->nlevels < n)
128 p->levels[p->nlevels++] = NULL;
129 }
130
levelset_free(levelset * p)131 void levelset_free(levelset *p) {
132 if (p) {
133 if (p->levels) {
134 int i;
135 for (i = 0; i < p->nlevels; i++)
136 level_free(p->levels[i]);
137 }
138 free(p);
139 }
140 }
141