178143775SMasatake YAMATO /*
278143775SMasatake YAMATO *
378143775SMasatake YAMATO * Copyright (c) 2016, Red Hat, Inc.
478143775SMasatake YAMATO * Copyright (c) 2016, Masatake YAMATO
578143775SMasatake YAMATO *
678143775SMasatake YAMATO * Author: Masatake YAMATO <yamato@redhat.com>
778143775SMasatake YAMATO *
878143775SMasatake YAMATO * This source code is released for free distribution under the terms of the
978143775SMasatake YAMATO * GNU General Public License version 2 or (at your option) any later version.
1078143775SMasatake YAMATO *
1178143775SMasatake YAMATO */
1278143775SMasatake YAMATO
1378143775SMasatake YAMATO #include "general.h" /* must always come first */
1478143775SMasatake YAMATO
159908a88aSMasatake YAMATO #include "debug.h"
1678143775SMasatake YAMATO #include "dependency.h"
17ce4ea610SMasatake YAMATO #include "options.h"
180d502ef0SMasatake YAMATO #include "parse_p.h"
193abcac5dSMasatake YAMATO #include "read.h"
20657cbb19SMasatake YAMATO #include "read_p.h"
2129e40fb6SMasatake YAMATO #include "routines.h"
22a53e10d8SMasatake YAMATO #include "subparser.h"
23bc924efdSMasatake YAMATO #include "subparser_p.h"
240d502ef0SMasatake YAMATO #include "xtag.h"
25355b5d96SMasatake YAMATO
26355b5d96SMasatake YAMATO #include <string.h>
27355b5d96SMasatake YAMATO
28edc12faeSMasatake YAMATO struct slaveControlBlock {
29edc12faeSMasatake YAMATO slaveParser *slaveParsers; /* The parsers on this list must be initialized when
30edc12faeSMasatake YAMATO this parser is initialized. */
31edc12faeSMasatake YAMATO subparser *subparsersDefault;
32edc12faeSMasatake YAMATO subparser *subparsersInUse;
33a641e930SMasatake YAMATO langType owner;
34edc12faeSMasatake YAMATO };
35edc12faeSMasatake YAMATO
linkDependencyAtInitializeParsing(depType dtype,parserDefinition * const master,struct slaveControlBlock * masterSCB,struct kindControlBlock * masterKCB,parserDefinition * const slave,struct kindControlBlock * slaveKCB,void * data)3678143775SMasatake YAMATO extern void linkDependencyAtInitializeParsing (depType dtype,
379908a88aSMasatake YAMATO parserDefinition *const master,
38edc12faeSMasatake YAMATO struct slaveControlBlock *masterSCB,
399a5a18e6SMasatake YAMATO struct kindControlBlock *masterKCB,
401c7bba36SMasatake YAMATO parserDefinition *const slave,
419a5a18e6SMasatake YAMATO struct kindControlBlock *slaveKCB,
421c7bba36SMasatake YAMATO void *data)
4378143775SMasatake YAMATO {
44355b5d96SMasatake YAMATO if (dtype == DEPTYPE_KIND_OWNER)
459a5a18e6SMasatake YAMATO linkKindDependency (masterKCB, slaveKCB);
46d86d3772SMasatake YAMATO else if (dtype == DEPTYPE_SUBPARSER || dtype == DEPTYPE_FOREIGNER)
47b88a2810SMasatake YAMATO {
489908a88aSMasatake YAMATO slaveParser *s = xMalloc (1, slaveParser);
49b88a2810SMasatake YAMATO
50fafdecadSMasatake YAMATO s->type = dtype;
519908a88aSMasatake YAMATO s->id = slave->id;
521c7bba36SMasatake YAMATO s->data = data;
53edc12faeSMasatake YAMATO
54edc12faeSMasatake YAMATO s->next = masterSCB->slaveParsers;
55edc12faeSMasatake YAMATO masterSCB->slaveParsers = s;
56b88a2810SMasatake YAMATO }
57b88a2810SMasatake YAMATO }
58b88a2810SMasatake YAMATO
attachSubparser(struct slaveControlBlock * base_sb,subparser * subparser)59edc12faeSMasatake YAMATO static void attachSubparser (struct slaveControlBlock *base_sb, subparser *subparser)
60edc12faeSMasatake YAMATO {
61edc12faeSMasatake YAMATO subparser->next = base_sb->subparsersDefault;
62edc12faeSMasatake YAMATO base_sb->subparsersDefault = subparser;
63edc12faeSMasatake YAMATO }
64edc12faeSMasatake YAMATO
65edc12faeSMasatake YAMATO
allocSlaveControlBlock(parserDefinition * parser)66a641e930SMasatake YAMATO extern struct slaveControlBlock *allocSlaveControlBlock (parserDefinition *parser)
67edc12faeSMasatake YAMATO {
68edc12faeSMasatake YAMATO struct slaveControlBlock *cb;
69edc12faeSMasatake YAMATO
70edc12faeSMasatake YAMATO cb = xMalloc (1, struct slaveControlBlock);
71edc12faeSMasatake YAMATO cb->slaveParsers = NULL;
72edc12faeSMasatake YAMATO cb->subparsersDefault = NULL;
73edc12faeSMasatake YAMATO cb->subparsersInUse = NULL;
74a641e930SMasatake YAMATO cb->owner = parser->id;
75edc12faeSMasatake YAMATO
76edc12faeSMasatake YAMATO return cb;
77edc12faeSMasatake YAMATO }
78edc12faeSMasatake YAMATO
freeSlaveControlBlock(struct slaveControlBlock * cb)79edc12faeSMasatake YAMATO extern void freeSlaveControlBlock (struct slaveControlBlock *cb)
80edc12faeSMasatake YAMATO {
81edc12faeSMasatake YAMATO eFree (cb);
82edc12faeSMasatake YAMATO }
83edc12faeSMasatake YAMATO
initializeDependencies(parserDefinition * parser,struct slaveControlBlock * cb)84edc12faeSMasatake YAMATO extern void initializeDependencies (parserDefinition *parser,
85edc12faeSMasatake YAMATO struct slaveControlBlock *cb)
86b88a2810SMasatake YAMATO {
879908a88aSMasatake YAMATO unsigned int i;
8862c9a9aaSMasatake YAMATO slaveParser *sp;
89b88a2810SMasatake YAMATO
909908a88aSMasatake YAMATO /* Initialize slaves */
91edc12faeSMasatake YAMATO sp = cb->slaveParsers;
92edc12faeSMasatake YAMATO while (sp != NULL)
93742653beSMasatake YAMATO {
94742653beSMasatake YAMATO if (sp->type == DEPTYPE_SUBPARSER)
95742653beSMasatake YAMATO {
96742653beSMasatake YAMATO subparser *sub;
97742653beSMasatake YAMATO
98742653beSMasatake YAMATO sub = (subparser *)sp->data;
99742653beSMasatake YAMATO sub->slaveParser = sp;
100742653beSMasatake YAMATO }
101742653beSMasatake YAMATO
102742653beSMasatake YAMATO if (sp->type == DEPTYPE_KIND_OWNER
103742653beSMasatake YAMATO || (sp->type == DEPTYPE_SUBPARSER &&
104b50486f4SMasatake YAMATO (((subparser *)sp->data)->direction & SUBPARSER_BASE_RUNS_SUB)))
105742653beSMasatake YAMATO {
106b88a2810SMasatake YAMATO initializeParser (sp->id);
1073abcac5dSMasatake YAMATO if (sp->type == DEPTYPE_SUBPARSER
10846a698ceSMasatake YAMATO && isXtagEnabled (XTAG_SUBPARSER))
1093abcac5dSMasatake YAMATO {
1103abcac5dSMasatake YAMATO subparser *subparser = sp->data;
1113abcac5dSMasatake YAMATO attachSubparser (cb, subparser);
1123abcac5dSMasatake YAMATO }
113742653beSMasatake YAMATO }
114edc12faeSMasatake YAMATO sp = sp->next;
115742653beSMasatake YAMATO }
11629f59ff5SMasatake YAMATO
11729f59ff5SMasatake YAMATO /* Initialize masters that act as base parsers. */
11829f59ff5SMasatake YAMATO for (i = 0; i < parser->dependencyCount; i++)
11929f59ff5SMasatake YAMATO {
12029f59ff5SMasatake YAMATO parserDependency *d = parser->dependencies + i;
121d86d3772SMasatake YAMATO if ((d->type == DEPTYPE_SUBPARSER &&
122742653beSMasatake YAMATO ((subparser *)(d->data))->direction & SUBPARSER_SUB_RUNS_BASE)
123d86d3772SMasatake YAMATO || (d->type == DEPTYPE_FOREIGNER))
12429f59ff5SMasatake YAMATO {
12529f59ff5SMasatake YAMATO langType baseParser;
12629f59ff5SMasatake YAMATO baseParser = getNamedLanguage (d->upperParser, 0);
12729f59ff5SMasatake YAMATO Assert (baseParser != LANG_IGNORE);
12829f59ff5SMasatake YAMATO initializeParser (baseParser);
12929f59ff5SMasatake YAMATO }
13029f59ff5SMasatake YAMATO }
131b88a2810SMasatake YAMATO }
132b88a2810SMasatake YAMATO
finalizeDependencies(parserDefinition * parser,struct slaveControlBlock * cb)133edc12faeSMasatake YAMATO extern void finalizeDependencies (parserDefinition *parser,
134edc12faeSMasatake YAMATO struct slaveControlBlock *cb)
135b88a2810SMasatake YAMATO {
136edc12faeSMasatake YAMATO while (cb->slaveParsers)
137edc12faeSMasatake YAMATO {
138edc12faeSMasatake YAMATO slaveParser *sp = cb->slaveParsers;
139edc12faeSMasatake YAMATO cb->slaveParsers = sp->next;
140edc12faeSMasatake YAMATO sp->next = NULL;
141faa60990SMasatake YAMATO eFree (sp);
14278143775SMasatake YAMATO }
143edc12faeSMasatake YAMATO }
144a53e10d8SMasatake YAMATO
notifyInputStart(void)145a53e10d8SMasatake YAMATO extern void notifyInputStart (void)
146a53e10d8SMasatake YAMATO {
147a53e10d8SMasatake YAMATO subparser *s;
148a53e10d8SMasatake YAMATO
149ee235db8SMasatake YAMATO /* for running prelude of optlib */
150ee235db8SMasatake YAMATO langType lang = getInputLanguage ();
1512db4cedcSMasatake YAMATO notifyLanguageRegexInputStart (lang);
1522db4cedcSMasatake YAMATO
153ee235db8SMasatake YAMATO foreachSubparser(s, true)
154a53e10d8SMasatake YAMATO {
155a53e10d8SMasatake YAMATO enterSubparser(s);
156ee235db8SMasatake YAMATO if (s->inputStart)
157a53e10d8SMasatake YAMATO s->inputStart (s);
158ee235db8SMasatake YAMATO /* propagate the event recursively */
159ee235db8SMasatake YAMATO notifyInputStart ();
160a53e10d8SMasatake YAMATO leaveSubparser();
161a53e10d8SMasatake YAMATO }
162a53e10d8SMasatake YAMATO }
163a53e10d8SMasatake YAMATO
notifyInputEnd(void)164a53e10d8SMasatake YAMATO extern void notifyInputEnd (void)
165a53e10d8SMasatake YAMATO {
166a53e10d8SMasatake YAMATO subparser *s;
167a53e10d8SMasatake YAMATO
168ee235db8SMasatake YAMATO foreachSubparser(s, true)
169a53e10d8SMasatake YAMATO {
170a53e10d8SMasatake YAMATO enterSubparser(s);
171ee235db8SMasatake YAMATO /* propagate the event recursively */
172ee235db8SMasatake YAMATO notifyInputEnd ();
173ee235db8SMasatake YAMATO if (s->inputEnd)
174a53e10d8SMasatake YAMATO s->inputEnd (s);
175a53e10d8SMasatake YAMATO leaveSubparser();
176a53e10d8SMasatake YAMATO }
1772db4cedcSMasatake YAMATO
178ee235db8SMasatake YAMATO /* for running sequel of optlib */
179ee235db8SMasatake YAMATO langType lang = getInputLanguage ();
1802db4cedcSMasatake YAMATO notifyLanguageRegexInputEnd (lang);
181a53e10d8SMasatake YAMATO }
182a53e10d8SMasatake YAMATO
notifyMakeTagEntry(const tagEntryInfo * tag,int corkIndex)1831ed0645cSMasatake YAMATO extern void notifyMakeTagEntry (const tagEntryInfo *tag, int corkIndex)
1841ed0645cSMasatake YAMATO {
1851ed0645cSMasatake YAMATO subparser *s;
1861ed0645cSMasatake YAMATO
1871ed0645cSMasatake YAMATO foreachSubparser(s, false)
1881ed0645cSMasatake YAMATO {
1891ed0645cSMasatake YAMATO if (s->makeTagEntryNotify)
1901ed0645cSMasatake YAMATO {
1911ed0645cSMasatake YAMATO enterSubparser(s);
1921ed0645cSMasatake YAMATO s->makeTagEntryNotify (s, tag, corkIndex);
1931ed0645cSMasatake YAMATO leaveSubparser();
1941ed0645cSMasatake YAMATO }
1951ed0645cSMasatake YAMATO }
1961ed0645cSMasatake YAMATO }
1971ed0645cSMasatake YAMATO
getSubparserLanguage(subparser * s)198a53e10d8SMasatake YAMATO extern langType getSubparserLanguage (subparser *s)
199a53e10d8SMasatake YAMATO {
200a53e10d8SMasatake YAMATO return s->slaveParser->id;
201a53e10d8SMasatake YAMATO }
202ce4ea610SMasatake YAMATO
chooseExclusiveSubparser(subparser * s,void * data)203ce4ea610SMasatake YAMATO extern void chooseExclusiveSubparser (subparser *s, void *data)
204ce4ea610SMasatake YAMATO {
205ce4ea610SMasatake YAMATO if (s->exclusiveSubparserChosenNotify)
206ce4ea610SMasatake YAMATO {
20709b4041bSMasatake YAMATO s->chosenAsExclusiveSubparser = true;
208ce4ea610SMasatake YAMATO enterSubparser(s);
209ce4ea610SMasatake YAMATO s->exclusiveSubparserChosenNotify (s, data);
210ce4ea610SMasatake YAMATO verbose ("%s is chosen as exclusive subparser\n",
211ce4ea610SMasatake YAMATO getLanguageName (getSubparserLanguage (s)));
212ce4ea610SMasatake YAMATO leaveSubparser();
213ce4ea610SMasatake YAMATO }
214ce4ea610SMasatake YAMATO }
215edc12faeSMasatake YAMATO
getFirstSubparser(struct slaveControlBlock * controlBlock)216edc12faeSMasatake YAMATO extern subparser *getFirstSubparser(struct slaveControlBlock *controlBlock)
217edc12faeSMasatake YAMATO {
218edc12faeSMasatake YAMATO if (controlBlock)
219edc12faeSMasatake YAMATO return controlBlock->subparsersInUse;
220edc12faeSMasatake YAMATO return NULL;
221edc12faeSMasatake YAMATO }
222edc12faeSMasatake YAMATO
useDefaultSubparsers(struct slaveControlBlock * controlBlock)223edc12faeSMasatake YAMATO extern void useDefaultSubparsers (struct slaveControlBlock *controlBlock)
224edc12faeSMasatake YAMATO {
225edc12faeSMasatake YAMATO controlBlock->subparsersInUse = controlBlock->subparsersDefault;
226edc12faeSMasatake YAMATO }
227edc12faeSMasatake YAMATO
useSpecifiedSubparser(struct slaveControlBlock * controlBlock,subparser * s)228edc12faeSMasatake YAMATO extern void useSpecifiedSubparser (struct slaveControlBlock *controlBlock, subparser *s)
229edc12faeSMasatake YAMATO {
230edc12faeSMasatake YAMATO s->schedulingBaseparserExplicitly = true;
231edc12faeSMasatake YAMATO controlBlock->subparsersInUse = s;
232edc12faeSMasatake YAMATO }
233edc12faeSMasatake YAMATO
setupSubparsersInUse(struct slaveControlBlock * controlBlock)234edc12faeSMasatake YAMATO extern void setupSubparsersInUse (struct slaveControlBlock *controlBlock)
235edc12faeSMasatake YAMATO {
236edc12faeSMasatake YAMATO if (!controlBlock->subparsersInUse)
237edc12faeSMasatake YAMATO useDefaultSubparsers(controlBlock);
238edc12faeSMasatake YAMATO }
239edc12faeSMasatake YAMATO
teardownSubparsersInUse(struct slaveControlBlock * controlBlock)240edc12faeSMasatake YAMATO extern subparser* teardownSubparsersInUse (struct slaveControlBlock *controlBlock)
241edc12faeSMasatake YAMATO {
242edc12faeSMasatake YAMATO subparser *tmp;
243edc12faeSMasatake YAMATO subparser *s = NULL;
244edc12faeSMasatake YAMATO
245edc12faeSMasatake YAMATO tmp = controlBlock->subparsersInUse;
246edc12faeSMasatake YAMATO controlBlock->subparsersInUse = NULL;
247edc12faeSMasatake YAMATO
248edc12faeSMasatake YAMATO if (tmp && tmp->schedulingBaseparserExplicitly)
249edc12faeSMasatake YAMATO {
250edc12faeSMasatake YAMATO tmp->schedulingBaseparserExplicitly = false;
251edc12faeSMasatake YAMATO s = tmp;
252edc12faeSMasatake YAMATO }
253edc12faeSMasatake YAMATO
254edc12faeSMasatake YAMATO if (s)
255edc12faeSMasatake YAMATO return s;
256edc12faeSMasatake YAMATO
257edc12faeSMasatake YAMATO while (tmp)
258edc12faeSMasatake YAMATO {
259edc12faeSMasatake YAMATO if (tmp->chosenAsExclusiveSubparser)
260edc12faeSMasatake YAMATO {
261edc12faeSMasatake YAMATO s = tmp;
262edc12faeSMasatake YAMATO }
263edc12faeSMasatake YAMATO tmp = tmp->next;
264edc12faeSMasatake YAMATO }
265edc12faeSMasatake YAMATO
266edc12faeSMasatake YAMATO return s;
267edc12faeSMasatake YAMATO }
2683abcac5dSMasatake YAMATO
2693abcac5dSMasatake YAMATO
2703abcac5dSMasatake YAMATO static int subparserDepth;
2713abcac5dSMasatake YAMATO
enterSubparser(subparser * subparser)2723abcac5dSMasatake YAMATO extern void enterSubparser(subparser *subparser)
2733abcac5dSMasatake YAMATO {
2743abcac5dSMasatake YAMATO subparserDepth++;
2753abcac5dSMasatake YAMATO pushLanguage (getSubparserLanguage (subparser));
2763abcac5dSMasatake YAMATO }
2773abcac5dSMasatake YAMATO
leaveSubparser(void)2783abcac5dSMasatake YAMATO extern void leaveSubparser(void)
2793abcac5dSMasatake YAMATO {
2803abcac5dSMasatake YAMATO popLanguage ();
2813abcac5dSMasatake YAMATO subparserDepth--;
2823abcac5dSMasatake YAMATO }
2833abcac5dSMasatake YAMATO
doesSubparserRun(void)2843abcac5dSMasatake YAMATO extern bool doesSubparserRun (void)
2853abcac5dSMasatake YAMATO {
286657cbb19SMasatake YAMATO if (getLanguageForBaseParser () == getInputLanguage())
287657cbb19SMasatake YAMATO return false;
2883abcac5dSMasatake YAMATO return subparserDepth;
2893abcac5dSMasatake YAMATO }
290c9ab038cSMasatake YAMATO
getFirstSlaveParser(struct slaveControlBlock * scb)291c9ab038cSMasatake YAMATO extern slaveParser *getFirstSlaveParser (struct slaveControlBlock *scb)
292c9ab038cSMasatake YAMATO {
293c9ab038cSMasatake YAMATO if (scb)
294c9ab038cSMasatake YAMATO return scb->slaveParsers;
295c9ab038cSMasatake YAMATO return NULL;
296c9ab038cSMasatake YAMATO }
297410a34d6SMasatake YAMATO
getLanguageSubparser(langType sublang,bool including_none_crafted_parser)29851258ebfSMasatake YAMATO extern subparser *getLanguageSubparser (langType sublang,
29951258ebfSMasatake YAMATO bool including_none_crafted_parser)
30051258ebfSMasatake YAMATO {
30151258ebfSMasatake YAMATO subparser *s;
30251258ebfSMasatake YAMATO
30351258ebfSMasatake YAMATO foreachSubparser (s, including_none_crafted_parser)
30451258ebfSMasatake YAMATO {
30551258ebfSMasatake YAMATO if (getSubparserLanguage (s) == sublang)
30651258ebfSMasatake YAMATO return s;
30751258ebfSMasatake YAMATO }
30851258ebfSMasatake YAMATO return NULL;
30951258ebfSMasatake YAMATO }
31051258ebfSMasatake YAMATO
subparserColprintTableNew(void)311406a9384SMasatake YAMATO extern struct colprintTable * subparserColprintTableNew (void)
312410a34d6SMasatake YAMATO {
313406a9384SMasatake YAMATO return colprintTableNew ("L:NAME", "L:BASEPARSER", "L:DIRECTIONS", NULL);
314410a34d6SMasatake YAMATO }
315410a34d6SMasatake YAMATO
subparserColprintAddSubparsers(struct colprintTable * table,struct slaveControlBlock * scb)316406a9384SMasatake YAMATO extern void subparserColprintAddSubparsers (struct colprintTable *table,
317406a9384SMasatake YAMATO struct slaveControlBlock *scb)
318410a34d6SMasatake YAMATO {
319410a34d6SMasatake YAMATO slaveParser *tmp;
320410a34d6SMasatake YAMATO
321410a34d6SMasatake YAMATO pushLanguage (scb->owner);
322410a34d6SMasatake YAMATO foreachSlaveParser(tmp)
323410a34d6SMasatake YAMATO {
324d86d3772SMasatake YAMATO if (tmp->type != DEPTYPE_SUBPARSER)
325d86d3772SMasatake YAMATO continue;
326d86d3772SMasatake YAMATO
327*4ecf2c99SMasatake YAMATO if (!isLanguageVisible (tmp->id))
328*4ecf2c99SMasatake YAMATO continue;
329*4ecf2c99SMasatake YAMATO
330406a9384SMasatake YAMATO struct colprintLine *line = colprintTableGetNewLine(table);
331410a34d6SMasatake YAMATO
332406a9384SMasatake YAMATO colprintLineAppendColumnCString (line, getLanguageName (tmp->id));
333406a9384SMasatake YAMATO colprintLineAppendColumnCString (line, getLanguageName (scb->owner));
334406a9384SMasatake YAMATO
335a7b49da1SColomban Wendling const char *direction;
336410a34d6SMasatake YAMATO switch (((subparser *)tmp->data)->direction)
337410a34d6SMasatake YAMATO {
338410a34d6SMasatake YAMATO case SUBPARSER_BASE_RUNS_SUB:
339f10db1c8SMasatake YAMATO direction = "base => sub {shared}";
340410a34d6SMasatake YAMATO break;
341410a34d6SMasatake YAMATO case SUBPARSER_SUB_RUNS_BASE:
342f10db1c8SMasatake YAMATO direction = "base <= sub {dedicated}";
343410a34d6SMasatake YAMATO break;
344410a34d6SMasatake YAMATO case SUBPARSER_BI_DIRECTION:
345f10db1c8SMasatake YAMATO direction = "base <> sub {bidirectional}";
346410a34d6SMasatake YAMATO break;
347410a34d6SMasatake YAMATO default:
348410a34d6SMasatake YAMATO direction = "UNKNOWN(INTERNAL BUG)";
349410a34d6SMasatake YAMATO break;
350410a34d6SMasatake YAMATO }
351406a9384SMasatake YAMATO colprintLineAppendColumnCString (line, direction);
352410a34d6SMasatake YAMATO }
353410a34d6SMasatake YAMATO popLanguage ();
354410a34d6SMasatake YAMATO }
355406a9384SMasatake YAMATO
subparserColprintCompareLines(struct colprintLine * a,struct colprintLine * b)356406a9384SMasatake YAMATO static int subparserColprintCompareLines (struct colprintLine *a , struct colprintLine *b)
357406a9384SMasatake YAMATO {
358406a9384SMasatake YAMATO const char *a_name = colprintLineGetColumn (a, 0);
359406a9384SMasatake YAMATO const char *b_name = colprintLineGetColumn (b, 0);
360406a9384SMasatake YAMATO
361406a9384SMasatake YAMATO int r;
362406a9384SMasatake YAMATO r = strcmp (a_name, b_name);
363406a9384SMasatake YAMATO if (r != 0)
364406a9384SMasatake YAMATO return r;
365406a9384SMasatake YAMATO
366406a9384SMasatake YAMATO const char *a_baseparser = colprintLineGetColumn (a, 1);
367406a9384SMasatake YAMATO const char *b_baseparser = colprintLineGetColumn (b, 1);
368406a9384SMasatake YAMATO
369406a9384SMasatake YAMATO return strcmp(a_baseparser, b_baseparser);
370406a9384SMasatake YAMATO }
371406a9384SMasatake YAMATO
subparserColprintTablePrint(struct colprintTable * table,bool withListHeader,bool machinable,FILE * fp)372406a9384SMasatake YAMATO extern void subparserColprintTablePrint (struct colprintTable *table,
373406a9384SMasatake YAMATO bool withListHeader, bool machinable, FILE *fp)
374406a9384SMasatake YAMATO {
375406a9384SMasatake YAMATO colprintTableSort (table, subparserColprintCompareLines);
376406a9384SMasatake YAMATO colprintTablePrint (table, 0, withListHeader, machinable, fp);
377406a9384SMasatake YAMATO }
378