1dnl PSPP - a program for statistical analysis.
2dnl Copyright (C) 2017 Free Software Foundation, Inc.
3dnl
4dnl This program is free software: you can redistribute it and/or modify
5dnl it under the terms of the GNU General Public License as published by
6dnl the Free Software Foundation, either version 3 of the License, or
7dnl (at your option) any later version.
8dnl
9dnl This program is distributed in the hope that it will be useful,
10dnl but WITHOUT ANY WARRANTY; without even the implied warranty of
11dnl MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12dnl GNU General Public License for more details.
13dnl
14dnl You should have received a copy of the GNU General Public License
15dnl along with this program.  If not, see <http://www.gnu.org/licenses/>.
16dnl
17AT_BANNER([syntax scanning])
18m4_define([PSPP_CHECK_SCAN],
19  [sed 's/^-//' < expout-base > expout
20   AT_CHECK([scan-test $1 input], [0], [expout])
21
22   sed '/^-/d' < expout-base > expout
23   AT_CHECK([scan-test -s $1 input], [0], [expout])])
24
25AT_SETUP([identifiers])
26AT_KEYWORDS([scan])
27AT_DATA([input], [dnl
28a aB i5 $x @efg @@. #.# .x _z.
29abcd. abcd.
30QRSTUV./* end of line comment */
31QrStUv./* end of line comment */ @&t@
32WXYZ. /* unterminated end of line comment
33�. /* U+FFFD is not valid in an identifier
34])
35AT_DATA([expout-base], [dnl
36ID "a"
37SKIP
38ID "aB"
39SKIP
40ID "i5"
41SKIP
42ID "$x"
43SKIP
44ID "@efg"
45SKIP
46ID "@@."
47SKIP
48ID "#.#"
49SKIP
50UNEXPECTED_DOT
51ID "x"
52SKIP
53UNEXPECTED_CHAR 95
54ID "z"
55ENDCMD
56SKIP
57ID "abcd."
58SKIP
59ID "abcd"
60ENDCMD
61SKIP
62ID "QRSTUV"
63ENDCMD
64SKIP
65SKIP
66ID "QrStUv"
67ENDCMD
68SKIP
69SKIP
70SKIP
71ID "WXYZ"
72ENDCMD
73SKIP
74SKIP
75SKIP
76UNEXPECTED_CHAR 65533
77ENDCMD
78SKIP
79SKIP
80-SKIP
81STOP
82])
83PSPP_CHECK_SCAN([-i])
84AT_CLEANUP
85
86AT_SETUP([reserved words])
87AT_KEYWORDS([scan])
88AT_DATA([input], [dnl
89and or not eq ge gt le lt ne all by to with
90AND OR NOT EQ GE GT LE LT NE ALL BY TO WITH
91andx orx notx eqx gex gtx lex ltx nex allx byx tox withx
92and. with.
93])
94AT_DATA([expout-base], [dnl
95AND
96SKIP
97OR
98SKIP
99NOT
100SKIP
101EQ
102SKIP
103GE
104SKIP
105GT
106SKIP
107LE
108SKIP
109LT
110SKIP
111NE
112SKIP
113ALL
114SKIP
115BY
116SKIP
117TO
118SKIP
119WITH
120SKIP
121AND
122SKIP
123OR
124SKIP
125NOT
126SKIP
127EQ
128SKIP
129GE
130SKIP
131GT
132SKIP
133LE
134SKIP
135LT
136SKIP
137NE
138SKIP
139ALL
140SKIP
141BY
142SKIP
143TO
144SKIP
145WITH
146SKIP
147ID "andx"
148SKIP
149ID "orx"
150SKIP
151ID "notx"
152SKIP
153ID "eqx"
154SKIP
155ID "gex"
156SKIP
157ID "gtx"
158SKIP
159ID "lex"
160SKIP
161ID "ltx"
162SKIP
163ID "nex"
164SKIP
165ID "allx"
166SKIP
167ID "byx"
168SKIP
169ID "tox"
170SKIP
171ID "withx"
172SKIP
173ID "and."
174SKIP
175WITH
176ENDCMD
177-SKIP
178STOP
179])
180PSPP_CHECK_SCAN([-i])
181AT_CLEANUP
182
183AT_SETUP([punctuation])
184AT_KEYWORDS([scan])
185AT_DATA([input], [dnl
186~ & | = >= > <= < ~= <> ( ) , - + * / [[ ]] **
187~&|=>=><=<~=<>(),-+*/[[]]**
188])
189AT_DATA([expout-base], [dnl
190NOT
191SKIP
192AND
193SKIP
194OR
195SKIP
196EQUALS
197SKIP
198GE
199SKIP
200GT
201SKIP
202LE
203SKIP
204LT
205SKIP
206NE
207SKIP
208NE
209SKIP
210LPAREN
211SKIP
212RPAREN
213SKIP
214COMMA
215SKIP
216DASH
217SKIP
218PLUS
219SKIP
220ASTERISK
221SKIP
222SLASH
223SKIP
224LBRACK
225SKIP
226RBRACK
227SKIP
228EXP
229SKIP
230NOT
231AND
232OR
233EQUALS
234GE
235GT
236LE
237LT
238NE
239NE
240LPAREN
241RPAREN
242COMMA
243DASH
244PLUS
245ASTERISK
246SLASH
247LBRACK
248RBRACK
249EXP
250-SKIP
251STOP
252])
253PSPP_CHECK_SCAN([-i])
254AT_CLEANUP
255
256AT_SETUP([numbers])
257AT_KEYWORDS([scan])
258AT_DATA([input], [dnl
2590 1 01 001. 1.
260123. /* comment 1 */ /* comment 2 */
261.1 0.1 00.1 00.10
2625e1 6E-1 7e+1 6E+01 6e-03
263.3E1 .4e-1 .5E+1 .6e+01 .7E-03
2641.23e1 45.6E-1 78.9e+1 99.9E+01 11.2e-03
265. 1e e1 1e+ 1e-
266])
267AT_DATA([expout-base], [dnl
268POS_NUM
269SKIP
270POS_NUM 1
271SKIP
272POS_NUM 1
273SKIP
274POS_NUM 1
275SKIP
276POS_NUM 1
277ENDCMD
278SKIP
279POS_NUM 123
280ENDCMD
281SKIP
282SKIP
283SKIP
284SKIP
285SKIP
286ENDCMD
287POS_NUM 1
288SKIP
289POS_NUM 0.1
290SKIP
291POS_NUM 0.1
292SKIP
293POS_NUM 0.1
294SKIP
295POS_NUM 50
296SKIP
297POS_NUM 0.6
298SKIP
299POS_NUM 70
300SKIP
301POS_NUM 60
302SKIP
303POS_NUM 0.006
304SKIP
305ENDCMD
306POS_NUM 30
307SKIP
308POS_NUM 0.04
309SKIP
310POS_NUM 5
311SKIP
312POS_NUM 6
313SKIP
314POS_NUM 0.0007
315SKIP
316POS_NUM 12.3
317SKIP
318POS_NUM 4.56
319SKIP
320POS_NUM 789
321SKIP
322POS_NUM 999
323SKIP
324POS_NUM 0.0112
325SKIP
326ENDCMD
327SKIP
328EXPECTED_EXPONENT "1e"
329SKIP
330ID "e1"
331SKIP
332EXPECTED_EXPONENT "1e+"
333SKIP
334EXPECTED_EXPONENT "1e-"
335-SKIP
336STOP
337])
338PSPP_CHECK_SCAN([-i])
339AT_CLEANUP
340
341AT_SETUP([strings])
342AT_KEYWORDS([scan])
343AT_DATA([input], [dnl
344'x' "y" 'abc'
345'Don''t' "Can't" 'Won''t'
346"""quoted""" '"quoted"'
347'' "" '''' """"
348'missing end quote
349"missing double quote
350'x' + "y"
351+ 'z' +
352'a' /* abc */ + "b" /*
353+ 'c' +/* */"d"/* */+'e'
354'foo'
355+          /* special case: + in column 0 would ordinarily start a new command
356'bar'
357'foo'
358 +
359'bar'
360'foo'
361+
362
363'bar'
364
365+
366x"4142"+'5152'
367"4142"+
368x'5152'
369x"4142"
370+u'304a'
371"�あいうえお"
372"abc"+U"FFFD"+u'3048'+"xyz"
373])
374AT_DATA([expout-base], [dnl
375STRING "x"
376SKIP
377STRING "y"
378SKIP
379STRING "abc"
380SKIP
381STRING "Don't"
382SKIP
383STRING "Can't"
384SKIP
385STRING "Won't"
386SKIP
387STRING ""quoted""
388SKIP
389STRING ""quoted""
390SKIP
391STRING ""
392SKIP
393STRING ""
394SKIP
395STRING "'"
396SKIP
397STRING """
398SKIP
399EXPECTED_QUOTE
400SKIP
401EXPECTED_QUOTE
402SKIP
403STRING "xyzabcde"
404SKIP
405STRING "foobar"
406SKIP
407STRING "foobar"
408SKIP
409STRING "foo"
410SKIP
411PLUS
412SKIP
413ENDCMD
414SKIP
415STRING "bar"
416SKIP
417ENDCMD
418SKIP
419PLUS
420SKIP
421STRING "AB5152"
422SKIP
423STRING "4142QR"
424SKIP
425STRING "ABお"
426SKIP
427STRING "�あいうえお"
428SKIP
429STRING "abc�えxyz"
430-SKIP
431STOP
432])
433PSPP_CHECK_SCAN([-i])
434AT_CLEANUP
435
436AT_SETUP([@%:@! construct])
437AT_KEYWORDS([scan])
438AT_DATA([input], [dnl
439#! /usr/bin/pspp
440#! /usr/bin/pspp
441])
442AT_DATA([expout-base], [dnl
443SKIP
444SKIP
445ID "#"
446UNEXPECTED_CHAR 33
447SKIP
448SLASH
449ID "usr"
450SLASH
451ID "bin"
452SLASH
453ID "pspp"
454-SKIP
455STOP
456])
457PSPP_CHECK_SCAN([-i])
458AT_CLEANUP
459
460AT_SETUP([* and COMMENT commands])
461AT_KEYWORDS([scan])
462AT_DATA([input], [dnl
463* Comment commands "don't
464have to contain valid tokens.
465
466** Check ambiguity with ** token.
467****************.
468
469comment keyword works too.
470COMM also.
471com is ambiguous with COMPUTE.
472
473   * Comment need not start at left margin.
474
475* Comment ends with blank line
476
477next command.
478
479])
480AT_DATA([expout-base], [dnl
481SKIP
482SKIP
483SKIP
484ENDCMD
485SKIP
486ENDCMD
487SKIP
488SKIP
489ENDCMD
490SKIP
491SKIP
492ENDCMD
493SKIP
494ENDCMD
495SKIP
496SKIP
497ENDCMD
498SKIP
499SKIP
500ENDCMD
501SKIP
502ID "com"
503SKIP
504ID "is"
505SKIP
506ID "ambiguous"
507SKIP
508WITH
509SKIP
510ID "COMPUTE"
511ENDCMD
512SKIP
513ENDCMD
514SKIP
515SKIP
516SKIP
517ENDCMD
518SKIP
519ENDCMD
520SKIP
521SKIP
522SKIP
523ENDCMD
524SKIP
525ID "next"
526SKIP
527ID "command"
528ENDCMD
529SKIP
530-ENDCMD
531-SKIP
532STOP
533])
534PSPP_CHECK_SCAN([-i])
535AT_CLEANUP
536
537AT_SETUP([DOCUMENT command])
538AT_KEYWORDS([scan])
539AT_DATA([input], [dnl
540DOCUMENT one line.
541DOC more
542    than
543        one
544            line.
545docu
546first.paragraph
547isn't parsed as tokens
548
549second paragraph.
550])
551AT_DATA([expout-base], [dnl
552ID "DOCUMENT"
553STRING "DOCUMENT one line."
554ENDCMD
555ENDCMD
556SKIP
557ID "DOCUMENT"
558STRING "DOC more"
559SKIP
560STRING "    than"
561SKIP
562STRING "        one"
563SKIP
564STRING "            line."
565ENDCMD
566ENDCMD
567SKIP
568ID "DOCUMENT"
569STRING "docu"
570SKIP
571STRING "first.paragraph"
572SKIP
573STRING "isn't parsed as tokens"
574SKIP
575STRING ""
576SKIP
577STRING "second paragraph."
578-ENDCMD
579-ENDCMD
580-SKIP
581STOP
582])
583PSPP_CHECK_SCAN([-i])
584AT_CLEANUP
585
586AT_SETUP([TITLE, SUBTITLE, FILE LABEL commands])
587AT_KEYWORDS([scan])
588AT_DATA([input], [dnl
589title/**/'Quoted string title'.
590tit /*
591"Quoted string on second line".
592sub "Quoted string subtitle"
593 .
594
595TITL /* Not a */ quoted string title.
596SUBT Not a quoted string /* subtitle
597
598FIL label isn't quoted.
599FILE
600  lab 'is quoted'.
601FILE /*
602/**/  lab not quoted here either
603
604])
605AT_DATA([expout-base], [dnl
606ID "title"
607SKIP
608STRING "Quoted string title"
609ENDCMD
610SKIP
611ID "tit"
612SKIP
613SKIP
614SKIP
615STRING "Quoted string on second line"
616ENDCMD
617SKIP
618ID "sub"
619SKIP
620STRING "Quoted string subtitle"
621SKIP
622SKIP
623ENDCMD
624SKIP
625ENDCMD
626SKIP
627ID "TITL"
628SKIP
629STRING "/* Not a */ quoted string title"
630ENDCMD
631SKIP
632ID "SUBT"
633SKIP
634STRING "Not a quoted string /* subtitle"
635SKIP
636ENDCMD
637SKIP
638ID "FIL"
639SKIP
640ID "label"
641SKIP
642STRING "isn't quoted"
643ENDCMD
644SKIP
645ID "FILE"
646SKIP
647SKIP
648ID "lab"
649SKIP
650STRING "is quoted"
651ENDCMD
652SKIP
653ID "FILE"
654SKIP
655SKIP
656SKIP
657SKIP
658SKIP
659ID "lab"
660SKIP
661STRING "not quoted here either"
662SKIP
663-ENDCMD
664-SKIP
665STOP
666])
667PSPP_CHECK_SCAN([-i])
668AT_CLEANUP
669
670AT_SETUP([BEGIN DATA command])
671AT_KEYWORDS([scan])
672AT_DATA([input], [dnl
673begin data.
674123
675xxx
676end data.
677
678BEG /**/ DAT /*
6795 6 7 /* x
680
681end  data
682end data
683.
684])
685AT_DATA([expout-base], [dnl
686ID "begin"
687SKIP
688ID "data"
689ENDCMD
690SKIP
691STRING "123"
692SKIP
693STRING "xxx"
694SKIP
695ID "end"
696SKIP
697ID "data"
698ENDCMD
699SKIP
700ENDCMD
701SKIP
702ID "BEG"
703SKIP
704SKIP
705SKIP
706ID "DAT"
707SKIP
708SKIP
709SKIP
710STRING "5 6 7 /* x"
711SKIP
712STRING ""
713SKIP
714STRING "end  data"
715SKIP
716ID "end"
717SKIP
718ID "data"
719SKIP
720ENDCMD
721-SKIP
722STOP
723])
724PSPP_CHECK_SCAN([-i])
725AT_CLEANUP
726
727AT_SETUP([DO REPEAT command])
728AT_KEYWORDS([scan])
729AT_DATA([input], [dnl
730do repeat x=a b c
731          y=d e f.
732  do repeat a=1 thru 5.
733another command.
734second command
735+ third command.
736end /* x */ /* y */ repeat print.
737end
738 repeat.
739])
740AT_DATA([expout-base], [dnl
741ID "do"
742SKIP
743ID "repeat"
744SKIP
745ID "x"
746EQUALS
747ID "a"
748SKIP
749ID "b"
750SKIP
751ID "c"
752SKIP
753SKIP
754ID "y"
755EQUALS
756ID "d"
757SKIP
758ID "e"
759SKIP
760ID "f"
761ENDCMD
762SKIP
763STRING "  do repeat a=1 thru 5."
764SKIP
765STRING "another command."
766SKIP
767STRING "second command"
768SKIP
769STRING "+ third command."
770SKIP
771STRING "end /* x */ /* y */ repeat print."
772SKIP
773ID "end"
774SKIP
775SKIP
776ID "repeat"
777ENDCMD
778-SKIP
779STOP
780])
781PSPP_CHECK_SCAN([-i])
782AT_CLEANUP
783
784AT_SETUP([batch mode])
785AT_KEYWORDS([scan])
786AT_DATA([input], [dnl
787first command
788     another line of first command
789+  second command
790third command
791
792fourth command.
793   fifth command.
794])
795AT_DATA([expout-base], [dnl
796ID "first"
797SKIP
798ID "command"
799SKIP
800SKIP
801ID "another"
802SKIP
803ID "line"
804SKIP
805ID "of"
806SKIP
807ID "first"
808SKIP
809ID "command"
810SKIP
811ENDCMD
812SKIP
813ID "second"
814SKIP
815ID "command"
816SKIP
817ENDCMD
818ID "third"
819SKIP
820ID "command"
821SKIP
822ENDCMD
823SKIP
824ID "fourth"
825SKIP
826ID "command"
827ENDCMD
828SKIP
829SKIP
830ID "fifth"
831SKIP
832ID "command"
833ENDCMD
834-SKIP
835STOP
836])
837PSPP_CHECK_SCAN([-b])
838AT_CLEANUP
839