1 |
/* |
2 |
* Dynamic String Utilities |
3 |
* |
4 |
* Taken from the tcl collection. - September 21, 1995 |
5 |
* by Kirk Abbott, and lightly modified to suit the neeeds of |
6 |
* ASCEND. |
7 |
* |
8 |
* Version: $Revision: 1.1 $ |
9 |
* Version control file: $RCSfile: dstring.c,v $ |
10 |
* Date last modified: $Date: 1997/07/18 11:41:34 $ |
11 |
* Last modified by: $Author: mthomas $ |
12 |
* |
13 |
* This file is part of the Ascend Language Interpreter. |
14 |
* |
15 |
* Copyright (C) 1990, 1993, 1994 Thomas Guthrie Epperly |
16 |
* |
17 |
* The Ascend Language Interpreter is free software; you can redistribute |
18 |
* it and/or modify it under the terms of the GNU General Public License as |
19 |
* published by the Free Software Foundation; either version 2 of the |
20 |
* License, or (at your option) any later version. |
21 |
* |
22 |
* The Ascend Language Interpreter is distributed in hope that it will be |
23 |
* useful, but WITHOUT ANY WARRANTY; without even the implied warranty of |
24 |
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU |
25 |
* General Public License for more details. |
26 |
* |
27 |
* You should have received a copy of the GNU General Public License |
28 |
* along with the program; if not, write to the Free Software Foundation, |
29 |
* Inc., 675 Mass Ave, Cambridge, MA 02139 USA. Check the file named |
30 |
* COPYING. |
31 |
* |
32 |
*/ |
33 |
|
34 |
#include "utilities/ascConfig.h" |
35 |
#include "utilities/ascMalloc.h" |
36 |
#include "utilities/ascPanic.h" |
37 |
#include "general/dstring.h" |
38 |
|
39 |
|
40 |
void Asc_DStringInit(register Asc_DString *dsPtr) |
41 |
{ |
42 |
asc_assert(NULL != dsPtr); |
43 |
dsPtr->string = dsPtr->staticSpace; |
44 |
dsPtr->length = 0; |
45 |
dsPtr->spaceAvl = ASC_DSTRING_STATIC_SIZE; |
46 |
dsPtr->staticSpace[0] = '\0'; |
47 |
} |
48 |
|
49 |
|
50 |
char *Asc_DStringSet(Asc_DString *dsPtr, CONST char *string) |
51 |
{ |
52 |
int length; |
53 |
char *newString; |
54 |
|
55 |
asc_assert(NULL != dsPtr); |
56 |
asc_assert(NULL != string); |
57 |
asc_assert((int)(MAXINT - strlen(string)) >= 0); |
58 |
|
59 |
length = (int)strlen(string); |
60 |
|
61 |
/* |
62 |
* Allocate a larger buffer for the string if the current one isn't |
63 |
* large enough. Allocate extra space in the new buffer so that there |
64 |
* will be room to grow before we have to allocate again. |
65 |
*/ |
66 |
if (length >= dsPtr->spaceAvl) { |
67 |
dsPtr->spaceAvl = length*2; |
68 |
newString = (char *) ascmalloc((size_t) dsPtr->spaceAvl); |
69 |
if (dsPtr->string != dsPtr->staticSpace) { |
70 |
ascfree(dsPtr->string); |
71 |
} |
72 |
dsPtr->string = newString; |
73 |
} |
74 |
|
75 |
/* |
76 |
* Copy the new string into the buffer |
77 |
*/ |
78 |
strncpy(dsPtr->string, string, (size_t)length); |
79 |
dsPtr->length = length; |
80 |
dsPtr->string[dsPtr->length] = '\0'; |
81 |
return dsPtr->string; |
82 |
} |
83 |
|
84 |
|
85 |
|
86 |
char *Asc_DStringAppend(register Asc_DString *dsPtr, |
87 |
CONST char *string, |
88 |
int length) |
89 |
{ |
90 |
int str_length; |
91 |
int newSize; |
92 |
char *newString; |
93 |
|
94 |
asc_assert(NULL != dsPtr); |
95 |
asc_assert(NULL != string); |
96 |
asc_assert((int)(MAXINT - strlen(string)) >= 0); |
97 |
|
98 |
str_length = (int)strlen(string); |
99 |
|
100 |
if (length < 0) { |
101 |
length = str_length; |
102 |
} |
103 |
else { |
104 |
length = MIN(length, str_length); |
105 |
} |
106 |
|
107 |
newSize = length + dsPtr->length; |
108 |
|
109 |
/* |
110 |
* Allocate a larger buffer for the string if the current one isn't |
111 |
* large enough. Allocate extra space in the new buffer so that there |
112 |
* will be room to grow before we have to allocate again. |
113 |
*/ |
114 |
if (newSize >= dsPtr->spaceAvl) { |
115 |
dsPtr->spaceAvl = newSize*2; |
116 |
newString = (char *) ascmalloc((size_t) dsPtr->spaceAvl); |
117 |
strcpy(newString, dsPtr->string); |
118 |
if (dsPtr->string != dsPtr->staticSpace) { |
119 |
ascfree(dsPtr->string); |
120 |
} |
121 |
dsPtr->string = newString; |
122 |
} |
123 |
|
124 |
/* |
125 |
* Copy the new string into the buffer at the end of the old one. |
126 |
*/ |
127 |
strncpy(dsPtr->string + dsPtr->length, string, (size_t)length); |
128 |
dsPtr->length += length; |
129 |
dsPtr->string[dsPtr->length] = '\0'; |
130 |
return dsPtr->string; |
131 |
} |
132 |
|
133 |
|
134 |
|
135 |
void Asc_DStringTrunc(register Asc_DString *dsPtr, int length) |
136 |
{ |
137 |
asc_assert(NULL != dsPtr); |
138 |
|
139 |
if (length < 0) { |
140 |
length = 0; |
141 |
} |
142 |
if (length < dsPtr->length) { |
143 |
dsPtr->length = length; |
144 |
dsPtr->string[length] = '\0'; |
145 |
} |
146 |
} |
147 |
|
148 |
|
149 |
|
150 |
void Asc_DStringFree(register Asc_DString *dsPtr) |
151 |
{ |
152 |
asc_assert(NULL != dsPtr); |
153 |
if (dsPtr->string != dsPtr->staticSpace) { |
154 |
ascfree(dsPtr->string); |
155 |
} |
156 |
dsPtr->string = dsPtr->staticSpace; |
157 |
dsPtr->length = 0; |
158 |
dsPtr->spaceAvl = ASC_DSTRING_STATIC_SIZE; |
159 |
dsPtr->staticSpace[0] = '\0'; |
160 |
} |
161 |
|
162 |
|
163 |
|
164 |
char *Asc_DStringResult(Asc_DString *dsPtr) |
165 |
{ |
166 |
register char *result; |
167 |
|
168 |
asc_assert (NULL != dsPtr); |
169 |
result = (char *)ascmalloc(strlen(dsPtr->string)+1); |
170 |
strcpy(result,dsPtr->string); |
171 |
Asc_DStringFree(dsPtr); |
172 |
return result; |
173 |
} |