4 * $Id: stack.c,v 4.13 2007/02/04 17:44:12 bkorb Exp $
5 * Time-stamp: "2007-01-13 10:43:21 bkorb"
7 * This is a special option processing routine that will save the
8 * argument to an option in a FIFO queue.
12 * Automated Options copyright 1992-2007 Bruce Korb
14 * Automated Options is free software.
15 * You may redistribute it and/or modify it under the terms of the
16 * GNU General Public License, as published by the Free Software
17 * Foundation; either version 2, or (at your option) any later version.
19 * Automated Options is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 * GNU General Public License for more details.
24 * You should have received a copy of the GNU General Public License
25 * along with Automated Options. See the file "COPYING". If not,
26 * write to: The Free Software Foundation, Inc.,
27 * 51 Franklin Street, Fifth Floor,
28 * Boston, MA 02110-1301, USA.
30 * As a special exception, Bruce Korb gives permission for additional
31 * uses of the text contained in his release of AutoOpts.
33 * The exception is that, if you link the AutoOpts library with other
34 * files to produce an executable, this does not by itself cause the
35 * resulting executable to be covered by the GNU General Public License.
36 * Your use of that executable is in no way restricted on account of
37 * linking the AutoOpts library code into it.
39 * This exception does not however invalidate any other reasons why
40 * the executable file might be covered by the GNU General Public License.
42 * This exception applies only to the code released by Bruce Korb under
43 * the name AutoOpts. If you copy code from other sources under the
44 * General Public License into a copy of AutoOpts, as the General Public
45 * License permits, the exception does not apply to the code that you add
46 * in this way. To avoid misleading anyone as to the status of such
47 * modified files, you must delete this exception notice from them.
49 * If you write modifications of your own for AutoOpts, it is your choice
50 * whether to permit this exception to apply to your modifications.
51 * If you do not wish that, delete this exception notice.
55 # include REGEX_HEADER
58 /*=export_func optionUnstackArg
61 * what: Remove option args from a stack
62 * arg: + tOptions* + pOpts + program options descriptor +
63 * arg: + tOptDesc* + pOptDesc + the descriptor for this arg +
66 * Invoked for options that are equivalenced to stacked options.
75 tArgList
* pAL
= (tArgList
*)pOptDesc
->optCookie
;
77 * IF we don't have any stacked options,
78 * THEN indicate that we don't have any of these options
81 pOptDesc
->fOptState
&= OPTST_PERSISTENT_MASK
;
82 if ( (pOptDesc
->fOptState
& OPTST_INITENABLED
) == 0)
83 pOptDesc
->fOptState
|= OPTST_DISABLED
;
92 if (regcomp( &re
, pOptDesc
->optArg
.argString
, REG_NOSUB
) != 0)
96 * search the list for the entry(s) to remove. Entries that
97 * are removed are *not* copied into the result. The source
98 * index is incremented every time. The destination only when
99 * we are keeping a define.
101 for (i
= 0, dIdx
= 0, ct
= pAL
->useCt
; --ct
>= 0; i
++) {
102 tCC
* pzSrc
= pAL
->apzArgs
[ i
];
103 char* pzEq
= strchr( pzSrc
, '=' );
108 res
= regexec( &re
, pzSrc
, (size_t)0, NULL
, 0 );
112 * Remove this entry by reducing the in-use count
113 * and *not* putting the string pointer back into
126 * IF we have dropped an entry
127 * THEN we have to move the current one.
130 pAL
->apzArgs
[ dIdx
] = pzSrc
;
137 #else /* not WITH_LIBREGEX */
142 * search the list for the entry(s) to remove. Entries that
143 * are removed are *not* copied into the result. The source
144 * index is incremented every time. The destination only when
145 * we are keeping a define.
147 for (i
= 0, dIdx
= 0, ct
= pAL
->useCt
; --ct
>= 0; i
++) {
148 tCC
* pzSrc
= pAL
->apzArgs
[ i
];
149 char* pzEq
= strchr( pzSrc
, '=' );
154 if (strcmp( pzSrc
, pOptDesc
->optArg
.argString
) == 0) {
156 * Remove this entry by reducing the in-use count
157 * and *not* putting the string pointer back into
167 * IF we have dropped an entry
168 * THEN we have to move the current one.
171 pAL
->apzArgs
[ dIdx
] = pzSrc
;
176 #endif /* WITH_LIBREGEX */
178 * IF we have unstacked everything,
179 * THEN indicate that we don't have any of these options
181 if (pAL
->useCt
== 0) {
182 pOptDesc
->fOptState
&= OPTST_PERSISTENT_MASK
;
183 if ( (pOptDesc
->fOptState
& OPTST_INITENABLED
) == 0)
184 pOptDesc
->fOptState
|= OPTST_DISABLED
;
185 AGFREE( (void*)pAL
);
186 pOptDesc
->optCookie
= NULL
;
192 * Put an entry into an argument list. The first argument points to
193 * a pointer to the argument list structure. It gets passed around
194 * as an opaque address.
197 addArgListEntry( void** ppAL
, void* entry
)
199 tArgList
* pAL
= *(void**)ppAL
;
202 * IF we have never allocated one of these,
203 * THEN allocate one now
206 pAL
= (tArgList
*)AGALOC( sizeof( *pAL
), "new option arg stack" );
210 pAL
->allocCt
= MIN_ARG_ALLOC_CT
;
215 * ELSE if we are out of room
216 * THEN make it bigger
218 else if (pAL
->useCt
>= pAL
->allocCt
) {
219 size_t sz
= sizeof( *pAL
);
220 pAL
->allocCt
+= INCR_ARG_ALLOC_CT
;
223 * The base structure contains space for MIN_ARG_ALLOC_CT
224 * pointers. We subtract it off to find our augment size.
226 sz
+= sizeof(char*) * (pAL
->allocCt
- MIN_ARG_ALLOC_CT
);
227 pAL
= (tArgList
*)AGREALOC( (void*)pAL
, sz
, "expanded opt arg stack" );
234 * Insert the new argument into the list
236 pAL
->apzArgs
[ (pAL
->useCt
)++ ] = entry
;
240 /*=export_func optionStackArg
243 * what: put option args on a stack
244 * arg: + tOptions* + pOpts + program options descriptor +
245 * arg: + tOptDesc* + pOptDesc + the descriptor for this arg +
248 * Keep an entry-ordered list of option arguments.
257 if (pOD
->optArg
.argString
== NULL
)
260 AGDUPSTR(pz
, pOD
->optArg
.argString
, "stack arg");
261 addArgListEntry( &(pOD
->optCookie
), (void*)pz
);
266 * c-file-style: "stroustrup"
267 * indent-tabs-mode: nil
269 * end of autoopts/stack.c */