1 |
johnpye |
485 |
/* ASCEND modelling environment |
2 |
|
|
Copyright (C) 1998 Carnegie Mellon University |
3 |
|
|
Copyright (C) 2006 Carnegie Mellon University |
4 |
aw0a |
1 |
|
5 |
johnpye |
485 |
This program is free software; you can redistribute it and/or modify |
6 |
|
|
it under the terms of the GNU General Public License as published by |
7 |
|
|
the Free Software Foundation; either version 2, or (at your option) |
8 |
|
|
any later version. |
9 |
aw0a |
1 |
|
10 |
johnpye |
485 |
This program is distributed in the hope that it will be useful, |
11 |
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of |
12 |
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
13 |
|
|
GNU General Public License for more details. |
14 |
aw0a |
1 |
|
15 |
johnpye |
485 |
You should have received a copy of the GNU General Public License |
16 |
|
|
along with this program; if not, write to the Free Software |
17 |
|
|
Foundation, Inc., 59 Temple Place - Suite 330, |
18 |
|
|
Boston, MA 02111-1307, USA. |
19 |
|
|
*//** |
20 |
|
|
@file |
21 |
|
|
This file defines and manages a little (we hope) |
22 |
|
|
database system for storing NOTES in-core in a variety |
23 |
|
|
of quickly accessible ways. |
24 |
|
|
|
25 |
|
|
If scale gets to be an issue, this could become a wrapper |
26 |
|
|
for a real database someday. |
27 |
|
|
|
28 |
|
|
This implementation is not optimized for anything -- the |
29 |
|
|
intent here is to learn if it can be done at all. |
30 |
|
|
*//* |
31 |
johnpye |
897 |
By Ben Allan 4/98 |
32 |
|
|
Last in CVS:$Revision: 1.3 $ $Date: 1998/06/16 16:38:42 $ $Author: mthomas $ |
33 |
johnpye |
485 |
*/ |
34 |
|
|
|
35 |
|
|
#ifndef ASC_NOTATE_H |
36 |
|
|
#define ASC_NOTATE_H |
37 |
|
|
|
38 |
johnpye |
1066 |
/** addtogroup compiler Compiler |
39 |
|
|
@{ |
40 |
|
|
*/ |
41 |
|
|
|
42 |
johnpye |
485 |
#include <utilities/ascConfig.h> |
43 |
johnpye |
897 |
#include <general/list.h> |
44 |
|
|
#include "compiler.h" |
45 |
|
|
#include "braced.h" |
46 |
johnpye |
485 |
|
47 |
johnpye |
897 |
/*------------------------------------------------------------------------------ |
48 |
|
|
MACROS AND DATA STRUCTURES |
49 |
|
|
*/ |
50 |
|
|
|
51 |
jds |
54 |
/** |
52 |
|
|
* A wildcard pointer value for database queries. |
53 |
|
|
* It is in the zero page, odd (which is impossible for |
54 |
|
|
* a symchar) and outside the range of the NoteData enum. |
55 |
aw0a |
1 |
*/ |
56 |
|
|
#define NOTESWILD ((symchar *)0x11) |
57 |
|
|
#define NOTESWILDLIST ((struct gl_list_t *)0x11) |
58 |
jds |
54 |
/**< |
59 |
|
|
* A wildcard list pointer value for database queries. |
60 |
|
|
* It is in the zero page, odd (which is impossible for |
61 |
|
|
* a symchar) and outside the range of the NoteData enum. |
62 |
|
|
*/ |
63 |
aw0a |
1 |
|
64 |
jds |
54 |
/** |
65 |
|
|
* Type of the void pointer which may be stored with a note. |
66 |
aw0a |
1 |
* We don't want to crap up this header with half the |
67 |
|
|
* compiler's includes because interface clients shouldn't |
68 |
|
|
* know. |
69 |
|
|
*/ |
70 |
|
|
enum NoteData { |
71 |
jds |
54 |
nd_wild, /**< Matches any in notes queries. */ |
72 |
|
|
nd_empty, /**< Pointer meaningless, should be NULL. matches only empty. */ |
73 |
|
|
nd_name, /**< struct Name * assumed someone else's to destroy. */ |
74 |
|
|
nd_vlist, /**< struct VariableList * ours to destroy. */ |
75 |
|
|
nd_module, /**< struct module_t * not ours, obviously. */ |
76 |
|
|
nd_anonymous /**< Future expansion as needed. */ |
77 |
aw0a |
1 |
}; |
78 |
|
|
|
79 |
jds |
54 |
/* contents none of your business. our persistent record. */ |
80 |
aw0a |
1 |
struct Note; |
81 |
|
|
|
82 |
jds |
54 |
/* wrapper for a regular expression matching engine. */ |
83 |
aw0a |
1 |
struct NoteEngine; |
84 |
|
|
|
85 |
jds |
54 |
/** Temporary for parser use only. Some fields (lang) may not be reset by client. |
86 |
|
|
* Do not store these anywhere permanently as they are not persistent. |
87 |
|
|
*/ |
88 |
aw0a |
1 |
struct NoteTmp { |
89 |
|
|
symchar *lang; |
90 |
|
|
struct bracechar *bt; |
91 |
|
|
void *vardata; |
92 |
|
|
int line; |
93 |
|
|
struct NoteTmp *next; |
94 |
|
|
}; |
95 |
|
|
|
96 |
johnpye |
897 |
/*------------------------------------------------------------------------------ |
97 |
|
|
TEMPORARY NOTES |
98 |
|
|
*/ |
99 |
aw0a |
1 |
|
100 |
johnpye |
480 |
/** |
101 |
jds |
54 |
* Create a notetmp for parsing NOTES statements. need this in order to |
102 |
aw0a |
1 |
* capture multiple fvarlist/bracedtext pairs for a single language key. |
103 |
|
|
*/ |
104 |
jds |
54 |
extern struct NoteTmp *CreateNoteTmp(symchar *lang, |
105 |
|
|
struct bracechar *bt, |
106 |
|
|
void *varlist, |
107 |
|
|
int line); |
108 |
aw0a |
1 |
|
109 |
jds |
54 |
/** Add a notetmp to a lifo (if you follow next) list. */ |
110 |
johnpye |
76 |
extern struct NoteTmp *LinkNoteTmp(struct NoteTmp *new_thing, |
111 |
jds |
54 |
struct NoteTmp *chain); |
112 |
aw0a |
1 |
|
113 |
johnpye |
480 |
/** |
114 |
jds |
54 |
* Destroy a chain of struct NoteTmp following the next pointers. |
115 |
aw0a |
1 |
* The bt and vardata fields contained (if any) are not destroyed. |
116 |
|
|
*/ |
117 |
jds |
54 |
extern void DestroyNoteTmpList(struct NoteTmp *head); |
118 |
aw0a |
1 |
|
119 |
johnpye |
897 |
/*------------------------------------------------------------------------------ |
120 |
|
|
REGULAR (PERSISTENT) NOTES |
121 |
|
|
*/ |
122 |
aw0a |
1 |
|
123 |
johnpye |
480 |
/** |
124 |
jds |
54 |
* Initialize the notes database. Returns 0 if successful. |
125 |
|
|
* Input is the symchar by which the database will be addressed. |
126 |
aw0a |
1 |
* The very first call to this function should be made with |
127 |
|
|
* NULL and merely initializes internal structures without |
128 |
|
|
* creating something according to dbid. That call always |
129 |
|
|
* returns 1. |
130 |
|
|
*/ |
131 |
johnpye |
1063 |
ASC_DLLSPEC int InitNotesDatabase(symchar *dbid); |
132 |
aw0a |
1 |
|
133 |
jds |
54 |
/** |
134 |
|
|
* Returns a gl_list containing symchar * of names (dbid) |
135 |
aw0a |
1 |
* of databases currently in existence. |
136 |
|
|
*/ |
137 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *ListNotesDatabases(void); |
138 |
aw0a |
1 |
|
139 |
johnpye |
480 |
/** |
140 |
jds |
54 |
* Destroy the database, and necessarily all tokens being held. |
141 |
aw0a |
1 |
* if dbid is 0x1, destroys all databases. |
142 |
|
|
*/ |
143 |
johnpye |
1063 |
ASC_DLLSPEC void DestroyNotesDatabase(symchar *dbid); |
144 |
aw0a |
1 |
|
145 |
johnpye |
480 |
/** |
146 |
jds |
54 |
* Clear any notes associated with the type named out of |
147 |
aw0a |
1 |
* database. Useful if replacing a type. |
148 |
|
|
*/ |
149 |
johnpye |
76 |
extern void DestroyNotesOnType(symchar *dbid, symchar *type_name); |
150 |
aw0a |
1 |
|
151 |
jds |
54 |
/** |
152 |
|
|
* Returns a list of notes matching the keys specified. |
153 |
|
|
* NOTESWILD key values are wildcards. |
154 |
aw0a |
1 |
* This list returned is yours to destroy. The contents of the |
155 |
|
|
* list are struct Note * and are Not yours to destroy. |
156 |
|
|
* |
157 |
jds |
54 |
* Examples: |
158 |
|
|
* <pre> |
159 |
aw0a |
1 |
* GetNotes(dbid,typename,NOTESWILD,NOTESWILD,NOTESWILD,nd_wild); |
160 |
|
|
* returns a list of all notes on a type or any part of the type. |
161 |
|
|
* This may contain apparent duplicates depending the Commit |
162 |
|
|
* optimizations that are performed. |
163 |
jds |
54 |
* |
164 |
aw0a |
1 |
* GetNotes(dbid,typename,language,NOTESWILD,NOTESWILD,nd_empty); |
165 |
|
|
* returns a list of all notes on a type in the given language |
166 |
|
|
* where the data slot is empty. |
167 |
jds |
54 |
* |
168 |
aw0a |
1 |
* GetNotes(dbid,typename,NOTESWILD,id,NULL,nd_empty); |
169 |
|
|
* returns a list of all notes on a type about id (including SELF) |
170 |
|
|
* in any language where method is NULL and no data is stored. |
171 |
jds |
54 |
* |
172 |
aw0a |
1 |
* GetNotes(dbid,typename,language,id,NULL,nd_empty); |
173 |
|
|
* returns a list of all notes on a type not in a method about id in language. |
174 |
jds |
54 |
* |
175 |
aw0a |
1 |
* GetNotes(dbid,NOTESWILD,NOTESWILD,id,NOTESWILD,nd_wild); |
176 |
|
|
* returns a list of all notes about id in any context, any language. |
177 |
jds |
54 |
* </pre> |
178 |
aw0a |
1 |
*/ |
179 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *GetNotes(symchar *dbid, |
180 |
jds |
54 |
symchar *type, |
181 |
|
|
symchar *lang, |
182 |
|
|
symchar *id, |
183 |
|
|
symchar *method, |
184 |
|
|
enum NoteData nd); |
185 |
aw0a |
1 |
|
186 |
jds |
54 |
/** |
187 |
aw0a |
1 |
* Given a pointer (alleged) to a note, checks that the |
188 |
|
|
* pointer is valid and returns a gl_list containing the |
189 |
|
|
* pointer. If the list is empty, the pointer is not valid. |
190 |
|
|
* This kind of boneheaded function is necessary for handling |
191 |
|
|
* scripted interfaces that can shove in garbage. |
192 |
|
|
* GetExactNote(dbid,n); |
193 |
|
|
*/ |
194 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *GetExactNote(symchar *dbid, struct Note *n); |
195 |
aw0a |
1 |
|
196 |
jds |
54 |
/** |
197 |
aw0a |
1 |
* Returns the list of notes matching any combination of the |
198 |
|
|
* keys stored in the gl_lists given. So, for example, |
199 |
|
|
* if you want the notes on id in typename or any ancestor, |
200 |
|
|
* cookup up the list of ancestor type names, stick id in idlist, |
201 |
|
|
* and pass NOTESWILD,nd_wild for the other two arguments. |
202 |
|
|
*/ |
203 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *GetNotesList(symchar *dbid, |
204 |
jds |
54 |
struct gl_list_t *types, |
205 |
|
|
struct gl_list_t *langs, |
206 |
|
|
struct gl_list_t *ids, |
207 |
|
|
struct gl_list_t *methods, |
208 |
|
|
struct gl_list_t *nds); |
209 |
aw0a |
1 |
|
210 |
johnpye |
480 |
/** |
211 |
jds |
54 |
* Return id of note. id is normally a child name or SELF. |
212 |
|
|
* Might be NULL. |
213 |
aw0a |
1 |
*/ |
214 |
johnpye |
1063 |
ASC_DLLSPEC symchar *GetNoteId(struct Note *n); |
215 |
aw0a |
1 |
|
216 |
johnpye |
480 |
/** |
217 |
jds |
54 |
* Return method of note. Method is normally NULL unless note |
218 |
|
|
* is in scope of a method. A note with nonNULL method might |
219 |
aw0a |
1 |
* also have a nonnull id. |
220 |
jds |
54 |
* Might be NULL. |
221 |
aw0a |
1 |
*/ |
222 |
johnpye |
1063 |
ASC_DLLSPEC symchar *GetNoteMethod(struct Note *n); |
223 |
aw0a |
1 |
|
224 |
johnpye |
480 |
/** |
225 |
|
|
* Return typename of note. |
226 |
jds |
54 |
* typename is normally something in the library. |
227 |
|
|
* Might be NULL. |
228 |
aw0a |
1 |
*/ |
229 |
johnpye |
1063 |
ASC_DLLSPEC symchar *GetNoteType(struct Note *n); |
230 |
aw0a |
1 |
|
231 |
jds |
54 |
/** Return language of note. Might be NULL. */ |
232 |
johnpye |
1063 |
ASC_DLLSPEC symchar *GetNoteLanguage(struct Note *n); |
233 |
aw0a |
1 |
|
234 |
johnpye |
480 |
/** |
235 |
|
|
* Return best module name of note. |
236 |
jds |
54 |
* Might be NULL. Name is string from a symchar. |
237 |
aw0a |
1 |
*/ |
238 |
johnpye |
1063 |
ASC_DLLSPEC CONST char *GetNoteFilename(struct Note *n); |
239 |
aw0a |
1 |
|
240 |
jds |
54 |
/** Return line number of note. possibly -1. */ |
241 |
johnpye |
1063 |
ASC_DLLSPEC int GetNoteLineNum(struct Note *n); |
242 |
aw0a |
1 |
|
243 |
jds |
54 |
/** Return the text string of a note. It is ours. */ |
244 |
johnpye |
1063 |
ASC_DLLSPEC struct bracechar *GetNoteText(struct Note *n); |
245 |
aw0a |
1 |
|
246 |
jds |
54 |
/** Return the enum NoteData. */ |
247 |
johnpye |
1063 |
ASC_DLLSPEC enum NoteData GetNoteEnum(struct Note *n); |
248 |
aw0a |
1 |
|
249 |
jds |
54 |
/** Return the data of a note if it matches the enum given, or NULL. */ |
250 |
johnpye |
1063 |
ASC_DLLSPEC void *GetNoteData(struct Note *n, enum NoteData nd); |
251 |
aw0a |
1 |
|
252 |
jds |
54 |
/** |
253 |
aw0a |
1 |
* Puts the list of note pointers on an internal tracking list. |
254 |
|
|
* token returned may be passed to Note functions which take a |
255 |
|
|
* token. Returns NULL on memory failure or on list nl not appearing |
256 |
|
|
* to contain notes. |
257 |
|
|
* The notes list must be from the same database. |
258 |
|
|
*/ |
259 |
johnpye |
1063 |
ASC_DLLSPEC void *HoldNoteData(symchar *dbid, struct gl_list_t *nl); |
260 |
aw0a |
1 |
|
261 |
jds |
54 |
/** |
262 |
aw0a |
1 |
* Returns NULL if token given is invalid in dbid. |
263 |
|
|
*/ |
264 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *HeldNotes(symchar *dbid, void *token); |
265 |
aw0a |
1 |
|
266 |
jds |
54 |
/** |
267 |
aw0a |
1 |
* Removes the list of note pointers associated with token |
268 |
|
|
* from internal tracking list. |
269 |
|
|
* Calling with a 0x1 token releases all held lists and all |
270 |
|
|
* existing tokens become invalid. |
271 |
|
|
* Calling with bogus token is ok. |
272 |
|
|
*/ |
273 |
johnpye |
1063 |
ASC_DLLSPEC void ReleaseNoteData(symchar *dbid, void *token); |
274 |
aw0a |
1 |
|
275 |
jds |
54 |
/** |
276 |
|
|
* Return the languages found in any committed note as a list of symchars. |
277 |
aw0a |
1 |
*/ |
278 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *GetNotesAllLanguages(symchar *dbid); |
279 |
aw0a |
1 |
|
280 |
jds |
54 |
/* |
281 |
aw0a |
1 |
* The 4 following calls do not work until after at least 1 call of |
282 |
|
|
* InitNotesDatabase(NULL) has been done. |
283 |
|
|
*/ |
284 |
|
|
|
285 |
jds |
54 |
/** Returns the 'Loaded Libraries' symchar, which is useful for the parser. */ |
286 |
johnpye |
1063 |
ASC_DLLSPEC symchar*LibraryNote(void); |
287 |
aw0a |
1 |
|
288 |
jds |
54 |
/** Returns the 'All Known Files' symchar, which is useful for the parser. */ |
289 |
aw0a |
1 |
extern symchar *GlobalNote(void); |
290 |
|
|
|
291 |
jds |
54 |
/** Returns the 'inline' symchar, which is useful for the parser. */ |
292 |
aw0a |
1 |
extern symchar *InlineNote(void); |
293 |
|
|
|
294 |
jds |
54 |
/** Returns the 'SELF' symchar, which is useful for the parser. */ |
295 |
aw0a |
1 |
extern symchar *SelfNote(void); |
296 |
|
|
|
297 |
jds |
54 |
/** |
298 |
|
|
* Add a note to the database. |
299 |
aw0a |
1 |
* Notes with vlists may be internally replicated to optimize |
300 |
|
|
* future queries. |
301 |
|
|
*/ |
302 |
jds |
54 |
extern int CommitNote(symchar *dbid, struct Note *note); |
303 |
aw0a |
1 |
|
304 |
jds |
54 |
/** |
305 |
aw0a |
1 |
* Create a note. Destroy the note unless you commit it to a |
306 |
|
|
* database. |
307 |
|
|
*/ |
308 |
jds |
54 |
extern struct Note *CreateNote(symchar *type, |
309 |
|
|
symchar *lang, |
310 |
|
|
symchar *id, |
311 |
|
|
symchar *method, |
312 |
|
|
CONST char *file, |
313 |
|
|
struct bracechar *btext, |
314 |
|
|
int line, |
315 |
|
|
VOIDPTR data, |
316 |
|
|
enum NoteData nd); |
317 |
aw0a |
1 |
|
318 |
johnpye |
480 |
/** |
319 |
jds |
54 |
* Destroys the note given, subject to reference counting. |
320 |
aw0a |
1 |
* Do not externally destroy a note once it has been committed to |
321 |
|
|
* the database. |
322 |
|
|
*/ |
323 |
jds |
54 |
extern void DestroyNote(struct Note *n); |
324 |
aw0a |
1 |
|
325 |
johnpye |
897 |
/*------------------------------------------------------------------------------ |
326 |
|
|
SEARCHING FUNCTIONS (LINK TO A REGULAR EXPRESSION ENGINE) |
327 |
|
|
*/ |
328 |
aw0a |
1 |
|
329 |
jds |
54 |
/** |
330 |
aw0a |
1 |
* Returns a list of notes whose text (or name list if a vlist note in future) |
331 |
|
|
* matches the pattern given according to the engine given. |
332 |
|
|
* If token is NULL, entire database is given, OTHERWISE token |
333 |
|
|
* must be a held note list. |
334 |
|
|
* Engine is the non-NULL return from a call to NotesCreateEngine. |
335 |
|
|
* The engine NEdata, about which you know more than we, |
336 |
|
|
* should be consulted for errors if the return is NULL. |
337 |
|
|
*/ |
338 |
johnpye |
1063 |
ASC_DLLSPEC struct gl_list_t *GetMatchingNotes(symchar *dbid, |
339 |
jds |
54 |
char *pattern, |
340 |
|
|
void *token, |
341 |
|
|
struct NoteEngine *engine); |
342 |
aw0a |
1 |
|
343 |
jds |
54 |
/** |
344 |
aw0a |
1 |
* An NEInitFunc takes whatever data was specified to the engine |
345 |
|
|
* and a string to be matched and prepares the engine for one or |
346 |
|
|
* more matches against that pattern. |
347 |
|
|
* NEInitFunc should return NULL if it fails to initialize, |
348 |
|
|
* else it should return a pointer to be used in processing strings. |
349 |
|
|
* Tcl_RegExpCompile is an example of this function class. |
350 |
|
|
*/ |
351 |
jds |
54 |
typedef void *(*NEInitFunc)(void *, /* NEdata */ |
352 |
|
|
char * /* pattern */); |
353 |
aw0a |
1 |
|
354 |
jds |
54 |
/** |
355 |
aw0a |
1 |
* An NECompareFunc returns -1 for error, 0 for no match, 1 for match. |
356 |
|
|
* Tcl_RegExpExec is an example of this function class. |
357 |
|
|
*/ |
358 |
jds |
54 |
typedef int (*NECompareFunc)(void *, /* NEdata */ |
359 |
|
|
void *, /* return from NEInitFunc */ |
360 |
|
|
char *, /* substring to test for match */ |
361 |
|
|
char * /* beginning of string containing |
362 |
aw0a |
1 |
* substring (^ matches) |
363 |
|
|
*/ |
364 |
|
|
); |
365 |
|
|
|
366 |
jds |
54 |
/** |
367 |
aw0a |
1 |
* This is a wrapper to keep things independent of anyone in particular's |
368 |
|
|
* regular expression package. |
369 |
|
|
*/ |
370 |
johnpye |
1063 |
ASC_DLLSPEC struct NoteEngine *NotesCreateEngine(void *NEdata, |
371 |
jds |
54 |
NEInitFunc NEInit, |
372 |
|
|
NECompareFunc NECompare); |
373 |
aw0a |
1 |
|
374 |
jds |
54 |
/** |
375 |
aw0a |
1 |
* Destroys a previously returned engine. |
376 |
|
|
*/ |
377 |
johnpye |
1063 |
ASC_DLLSPEC void NotesDestroyEngine(struct NoteEngine *engine); |
378 |
aw0a |
1 |
|
379 |
johnpye |
1066 |
/* @} */ |
380 |
|
|
|
381 |
johnpye |
485 |
#endif /* ASC_NOTATE_H */ |
382 |
jds |
54 |
|