├── .gitignore ├── images └── icon.png ├── screenshots ├── cl.png ├── cmd.png ├── mi.PNG ├── pf.PNG ├── pnlgrp.png ├── rpg400.png ├── sqlrpgle.PNG ├── rpglefixed.PNG └── rpglefree.PNG ├── tests ├── issues │ ├── 137.rpgle │ ├── 143.clle │ ├── 38.sqlrpgle │ ├── 163.rpgle │ ├── 49.rpgle │ ├── 30.sqlrpgle │ ├── 42.rpgle │ ├── 90.rpgle │ ├── 55.sqlrpgle │ ├── 135.clle │ ├── 85.sqlrpgle │ ├── 32.rpgle │ ├── 98.clle │ ├── 41.rpgle │ ├── 52.rpg │ ├── 35.dspf │ ├── 36.pf │ ├── 52.lf │ ├── 94.sqlrpgle │ ├── 97.clle │ ├── 29.rpgle │ ├── 58.mi │ ├── 104.rpgle │ ├── 48.rpgle │ ├── 63.rpgle │ ├── 84.rpgle │ ├── 80.rpgle │ ├── 124.pnlgrp │ ├── 141.pf │ ├── 52.rpgle │ ├── 66.sqlrpgle │ ├── 96.sqlrpgle │ ├── 82.rpgle │ ├── 106.rpgle │ ├── 115.rpgle │ ├── 83.rpgle │ ├── 52.pf │ ├── 102.sqlrpgle │ ├── 116.rpgle │ ├── 91.sqlrpgle │ ├── 101.sqlrpgle │ ├── 34.rpgle │ ├── 23.rpgle │ ├── 125.rpgle │ ├── 93.sqlrpgle │ ├── 114.rpgle │ ├── 59.sqlrpgle │ ├── 78.rpgle │ ├── 110.rpgle │ ├── 60.rpgle │ ├── 120.rpgle │ ├── 132.rpgle │ ├── 61.rpgle │ ├── 40.rpgle │ ├── 150.dspf │ ├── 108.clp │ ├── 57.rpgle │ ├── 136.clle │ ├── 136.rpgle │ ├── 152.dspf │ ├── 61.rpg │ ├── 136.cmd │ └── 54.sqlrpgle └── general │ ├── test.bnd │ ├── test.lf │ ├── test.icff │ ├── test2.dspf │ ├── test.pf │ ├── test-cl-comments.clle │ ├── test.prtf │ ├── test1.mi │ ├── sms.sqlrpgle │ ├── test.cmd │ ├── ifsread.rpgle │ ├── test.pnlgrp │ ├── test1.rpg │ ├── test-free.sqlrpgle │ ├── test2.rpg │ ├── test.dspf │ ├── test.clp │ ├── bfint.rpgle │ ├── test3.mi │ ├── test-fixed.rpgle │ ├── test-fullfree.rpgle │ └── test-free.rpgle ├── .vscodeignore ├── .gitattributes ├── dev ├── dds │ ├── pf.txt │ ├── lf.txt │ ├── icff.txt │ ├── prtf.txt │ └── dspf.txt ├── util.py ├── rpgle-fixed │ ├── rpgle-h.txt │ ├── rpgle-f.txt │ ├── rpgle-d.txt │ ├── rpgle-bif.txt │ └── rpgle-c.txt ├── rpgle-free │ ├── rpgle-file.txt │ ├── rpgle-control.txt │ └── rpgle-definition.txt ├── cl │ └── util.py ├── rpg400 │ ├── ops.txt │ └── notes.rpg ├── mi │ └── mi.txt └── sql │ └── keywords.txt ├── .vscode ├── settings.json └── launch.json ├── configurations ├── dds.language-configuration.json ├── mi.language-configuration.json ├── pnlgrp.language-configuration.json ├── cl.language-configuration.json ├── cmd.language-configuration.json ├── rpg.language-configuration.json └── rpgle.language-configuration.json ├── .github └── workflows │ └── main.yml ├── LICENSE ├── syntaxes ├── bnd.tmLanguage.json ├── dds.pf.tmLanguage.json ├── dds.lf.tmLanguage.json ├── cmd.tmLanguage.json ├── dds.icff.tmLanguage.json ├── dds.prtf.tmLanguage.json ├── mi.tmLanguage.json └── dds.dspf.tmLanguage.json ├── README.md └── package.json /.gitignore: -------------------------------------------------------------------------------- 1 | .wakatime-project 2 | !.vscode/launch.json 3 | node_modules 4 | *.vsix 5 | tests/.vscode/ -------------------------------------------------------------------------------- /images/icon.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/images/icon.png -------------------------------------------------------------------------------- /screenshots/cl.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/cl.png -------------------------------------------------------------------------------- /screenshots/cmd.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/cmd.png -------------------------------------------------------------------------------- /screenshots/mi.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/mi.PNG -------------------------------------------------------------------------------- /screenshots/pf.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/pf.PNG -------------------------------------------------------------------------------- /screenshots/pnlgrp.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/pnlgrp.png -------------------------------------------------------------------------------- /screenshots/rpg400.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/rpg400.png -------------------------------------------------------------------------------- /screenshots/sqlrpgle.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/sqlrpgle.PNG -------------------------------------------------------------------------------- /screenshots/rpglefixed.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/rpglefixed.PNG -------------------------------------------------------------------------------- /screenshots/rpglefree.PNG: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/HEAD/screenshots/rpglefree.PNG -------------------------------------------------------------------------------- /tests/issues/137.rpgle: -------------------------------------------------------------------------------- 1 | 2 | **free 3 | 4 | dcl-pr main extpgm('TESTR') end-pr; 5 | 6 | dcl-ds prtDs len(132) end-ds; 7 | -------------------------------------------------------------------------------- /.vscodeignore: -------------------------------------------------------------------------------- 1 | .vscode/** 2 | .vscode-test/** 3 | .gitignore 4 | vsc-extension-quickstart.md 5 | 6 | # test files # 7 | tests/** 8 | dev/** -------------------------------------------------------------------------------- /tests/issues/143.clle: -------------------------------------------------------------------------------- 1 | dspobjd obj(&lib/*all) objtype(*file) output(*outfile) outfile(qtemp/objects) /* vscode comment fix */ 2 | rtvmbrd qtemp/objects nbrcurrcd(&nbrcurrcd) 3 | -------------------------------------------------------------------------------- /.gitattributes: -------------------------------------------------------------------------------- 1 | *.json linguist-detectable=true 2 | *.py linguist-detectable=false 3 | 4 | # linguist mismatch 5 | *.clp linguist-detectable=false 6 | *.cmd linguist-detectable=false -------------------------------------------------------------------------------- /tests/issues/38.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | exec sql 4 | GROUP BY RRCLTP,rrclm#, 5 | poltp2, 6 | raplcy 7 | HAVING sum(rrpaym) >=500; -- Only payments exceeding $500 -------------------------------------------------------------------------------- /tests/issues/163.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | /if not defined(VAR) 4 | /define VAR 5 | /include file 6 | dcl-s v1 char(10); 7 | 8 | /title Hello 9 | /space 5 10 | 11 | // comment 12 | /endif 13 | -------------------------------------------------------------------------------- /tests/issues/49.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/49 4 | 5 | for AL3Ptr = NameCount + 1 to 5; 6 | ReturnLine(AL3Ptr) = *blanks; 7 | endfor; -------------------------------------------------------------------------------- /tests/issues/30.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/30 4 | 5 | // get current transaction 6 | exec SQL SET TRANSACTION ISOLATION LEVEL NO COMMIT; //open 7 | -------------------------------------------------------------------------------- /dev/dds/pf.txt: -------------------------------------------------------------------------------- 1 | ZONE|VARLEN|VALUES|UNSIGNED|UNIQUE|TIMSEP|TIMFMT|TEXT|REFSHIFT|REFFLD|REF|RANGE|NOALTSEQ|LIFO|FORMAT|FLTPCN|FIFO|FCFO|EDTCDE|EDTWRD|DIGIT|DFT|DESCEND|DATSEP|DATFMT|COMP|COLHDG|CMP|CHKMSGID|CHECK|CCSID|ALWNULL|ALTSEQ|ALIAS|ABSVAL -------------------------------------------------------------------------------- /tests/issues/42.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | fptr = fopen(fpath: fmode); 4 | line = fgets(%addr(buffer): %size(buffer): fptr); 5 | 6 | dow (line <> *NULL); 7 | buffer = %xlate(x'00250D' : ' ': buffer); // CR,LF,NULL 8 | enddo; -------------------------------------------------------------------------------- /tests/issues/90.rpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/90 2 | * 3 | H/TITLE Test fixed 4 | 5 | /FREE 6 | /TITLE Test free 7 | CTL-OPT DATFMT(*YMD) DATEDIT(*YMD) DEBUG(*YES); 8 | /END-FREE 9 | -------------------------------------------------------------------------------- /tests/general/test.bnd: -------------------------------------------------------------------------------- 1 | /* comment */ 2 | -- comment 3 | 4 | STRPGMEXP PGMLVL(*CURRENT) SIGNATURE('BND 1.0') LVLCHK(*NO) 5 | EXPORT SYMBOL(FUNC1) 6 | EXPORT SYMBOL(FUNC2) 7 | EXPORT SYMBOL(FUNC3<<<) 8 | EXPORT SYMBOL("FUNC4") 9 | ENDPGMEXP -------------------------------------------------------------------------------- /tests/issues/55.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/55 3 | 4 | Exec SQL 5 | select max(amt) into :CurrentAmt 6 | from some_table 7 | // where something something something <= 8 | ; -------------------------------------------------------------------------------- /tests/issues/135.clle: -------------------------------------------------------------------------------- 1 | 2 | RUNSQM REQUEST('SELECT * FROM QTEMP/RTVSRCF WHERE SUBSTR(SRCDTA, 6, 2)=''A '' AND SUBSTR(SRCDTA, 17, 1)=''R'' ') + 3 | OUTPUT(*OUTFILE) OUTFILE(QTEMP/RTVJOIN) MEMBER(*ADD/*FIRST) 4 | MONMSG MSGID(CPF0000) EXEC(GOTO CMDLBL(SQLERRORE)) 5 | -------------------------------------------------------------------------------- /dev/util.py: -------------------------------------------------------------------------------- 1 | # take list of opcodes, reverse it, and build regex 2 | 3 | ops = [] 4 | with open('sql/keywords.txt', 'r') as f: 5 | for line in f: 6 | ops.append(line.strip()) 7 | with open('sql/regex.json', 'w') as f: 8 | f.write('"' + ('|'.join(sorted(ops, reverse=True))) + '"') -------------------------------------------------------------------------------- /dev/dds/lf.txt: -------------------------------------------------------------------------------- 1 | ZONE|VARLEN|VALUES|UNSIGNED|UNIQUE|TIMSEP|TIMFMT|TEXT|SST|RENAME|REFSHIFT|REFACCPTH|RANGE|PFILE|NOALTSEQ|LIFO|JREF|JOIN|JFLD|JFILE|JDUPSEQ|JDFTVAL|FORMAT|FLTPCN|FIFO|FCFO|EDTCDE|EDTWRD|DYNSLT|DIGIT|DESCEND|DATSEP|DATFMT|CONCAT|COMP|COLHDG|CMP|CHKMSGID|CHECK|CCSID|ALTSEQ|ALL|ALIAS|ABSVAL -------------------------------------------------------------------------------- /tests/issues/85.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // haha wow I didn't notice this... 4 | 5 | dcl-s tabName char(64) inz(*blanks); 6 | tabName = 'OUTPUT_QUEUE_ENTRIES_BASIC'; 7 | 8 | exec sql 9 | select * 10 | from QSYS2.SYSTABLES 11 | where TABLE_OWNER='QSYS' 12 | and TABLE_NAME=:tabName 13 | ; -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "[json]": { 3 | "editor.defaultFormatter": "vscode.json-language-features", 4 | "editor.tabSize": 2, 5 | "editor.formatOnSave": true, 6 | "editor.insertSpaces": true, 7 | "editor.detectIndentation": false, 8 | "files.trimTrailingWhitespace": true, 9 | } 10 | } -------------------------------------------------------------------------------- /tests/issues/32.rpgle: -------------------------------------------------------------------------------- 1 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/32 2 | // 3 | // If error during update, exit: 4 | C *IN99 CABEQ *ON DAEXIT 5 | C ENDIF WKIPIN 6 | C ENDFOR -------------------------------------------------------------------------------- /dev/rpgle-fixed/rpgle-h.txt: -------------------------------------------------------------------------------- 1 | VALIDATE|USRPRF|TIMFMT|THREAD|TEXT|SRTSEQ|PRFDTA|OPTION|OPTIMIZE|OPENOPT|NOMAIN|MAIN|LANGID|INTPREC|INDENT|GENLVL|FTRANS|FORMSALIGN|FLTDIV|FIXNBR|EXTBININT|EXPROPTS|ENBPFRCOL|DFTNAME|DFTACTGRP|DECEDIT|DEBUG|DATFMT|DATEEDIT|CVTOPT|DCLOPT|CURSYM|COPYRIGHT|CCSIDCVT|CCSID|COPYNEST|BNDDIR|AUT|ALWNULL|ALTSEQ|ALLOC|ACTGRP -------------------------------------------------------------------------------- /dev/rpgle-fixed/rpgle-f.txt: -------------------------------------------------------------------------------- 1 | WORKSTN|USROPN|USAGE|TIMFMT|TEMPLATE|STATIC|SPECIAL|SLN|SFILE|SEQ|SAVEIND|SAVEDS|RENAME|RECNO|RAFDATA|QUALIFIED|PRTCTL|PRINTER|PREFIX|PLIST|PGMNAME|PASS|OFLIND|MAXDEV|LIKEFILE|KEYLOC|KEYED|INFSR|INFDS|INDDS|INCLUDE|IGNORE|HANDLER|FORMOFL|FORMLEN|EXTMBR|EXTIND|EXTFILE|EXTDESC|DISK|DEVID|DATFMT|DATA|COMMIT|BLOCK|ALIAS -------------------------------------------------------------------------------- /dev/rpgle-free/rpgle-file.txt: -------------------------------------------------------------------------------- 1 | WORKSTN|USROPN|USAGE|TIMFMT|TEMPLATE|STATIC|SPECIAL|SLN|SFILE|SEQ|SAVEIND|SAVEDS|RENAME|RECNO|RAFDATA|QUALIFIED|PRTCTL|PRINTER|PREFIX|PLIST|PGMNAME|PASS|OFLIND|MAXDEV|LIKEFILE|KEYLOC|KEYED|INFSR|INFDS|INDDS|INCLUDE|IGNORE|HANDLER|FORMOFL|FORMLEN|EXTMBR|EXTIND|EXTFILE|EXTDESC|DISK|DEVID|DATFMT|DATA|COMMIT|BLOCK|ALIAS -------------------------------------------------------------------------------- /tests/general/test.lf: -------------------------------------------------------------------------------- 1 | A* Logical file test 2 | * 3 | A R PERSFMT4 PFILE(PERSON) 4 | A PERSONID 5 | A FIRSTNAME 6 | A LASTNAME 7 | A AGE 8 | A K PERSONID 9 | A O AGE COMP(GT 30) 10 | A* -------------------------------------------------------------------------------- /tests/issues/98.clle: -------------------------------------------------------------------------------- 1 | /* https://github.com/barrettotte/vscode-ibmi-languages/issues/98 */ 2 | 3 | /* SOMELIB */ 4 | DSPFD FILE(SOMELIB/*ALL) TYPE(*MBR) + 5 | OUTPUT(*OUTFILE) FILEATR(*PF) OUTFILE(MY_OUT) 6 | CPYF FROMFILE(MY_PF) TOFILE(QTEMP/WORK) + 7 | MBROPT(*ADD) -------------------------------------------------------------------------------- /dev/dds/icff.txt: -------------------------------------------------------------------------------- 1 | VARLEN|VARBUFMGT|TNSSYNLVL|TIMER|TEXT|SYNLVL|SUBDEV|SECURITY|RSPCONFIRM|RQSWRT|REFFLD|REF|RECID|RCVTRNDRND|RCVTKCMT|RCVROLLB|RCVNEGRSP|RCVFMH|RCVFAIL|RCVENDGRP|RCVDETACH|RCVCTLDTA|RCVCONFIRM|RCVCANCEL|PRPCMT|NEGRSP|INVITE|INDTXT|INDARA|FRCDTA|FMTNAME|FMH|FLTPCN|FAIL|EVOKE|EOS|ENDGRP|DFREVOKE|DETACH|CTLDTA|CONFIRM|CNLINVITE|CANCEL|ALWWRT|ALIAS -------------------------------------------------------------------------------- /tests/issues/41.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/41 4 | 5 | dcl-pr openFile pointer extproc('_C_IFS_fopen'); 6 | *n pointer value; // file name 7 | *n pointer value; // file mode 8 | end-pr; 9 | 10 | dcl-pr main extpgm('IFSREAD'); 11 | *n char(127); 12 | *n char(4096); 13 | end-pr; 14 | -------------------------------------------------------------------------------- /tests/issues/52.rpg: -------------------------------------------------------------------------------- 1 | H* https://github.com/barrettotte/vscode-ibmi-languages/issues/52 2 | C* 3 | WASD C* 4 | OHMANC MOVEL'HELLO' HELLO 11 5 | C MOVE 'WORLD' HELLO 6 | TEST C HELLO DSPLY WAIT 1 7 | C SETON LR -------------------------------------------------------------------------------- /tests/issues/35.dspf: -------------------------------------------------------------------------------- 1 | A* https://github.com/barrettotte/vscode-ibmi-languages/issues/35 2 | * 3 | A DSPSIZ(24 80 *DS3) 4 | A REF(*LIBL/EQFREF) 5 | A INDARA 6 | * 7 | A* Resolved by strictly highlighting identifiers in all DDS regex -------------------------------------------------------------------------------- /dev/rpgle-free/rpgle-control.txt: -------------------------------------------------------------------------------- 1 | VALIDATE|USRPRF|TRUNCNBR|TIMFMT|THREAD|TEXT|STGMDL|SRTSEQ|PRFDTA|PGMINFO|OPTION|OPTIMIZE|OPENOPT|NOMAIN|MAIN|LANGID|INTPREC|INDENT|GENLVL|FTRANS|FORMSALIGN|FLTDIV|FIXNBR|EXTBININT|EXPROPTS|ENBPFRCOL|DFTNAME|DFTACTGRP|DECPREC|DECEDIT|DEBUG|DATFMT|DATEDIT|DCLOPT|CVTOPT|CURSYM|COPYRIGHT|COPYNEST|CCSIDCVT|CCSID|BNDDIR|AUT|ALWNULL|ALTSEQ|ACTGRP|ALLOC -------------------------------------------------------------------------------- /tests/issues/36.pf: -------------------------------------------------------------------------------- 1 | A* https://github.com/barrettotte/vscode-ibmi-languages/issues/36 2 | * 3 | A TLEXR2 R COLHDG('Kypc конвертации' 'вапюты + 4 | A BIN-A' 'вапюту счета') 5 | * 6 | * Resolved, I forgot to move this regex to every DDS file. 7 | * Previously, it was only in DSPF and RPGLE -------------------------------------------------------------------------------- /tests/issues/52.lf: -------------------------------------------------------------------------------- 1 | A* Logical file test 2 | * 3 | A R PERSFMT4 PFILE(PERSON) 4 | A PERSONID TEXT('* TESTING...') 5 | WASD A FIRSTNAME 6 | A LASTNAME 7 | ADDDDA AGE 8 | A K PERSONID 9 | A O AGE COMP(GT 30) 10 | TEST A* -------------------------------------------------------------------------------- /tests/issues/94.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/94 3 | 4 | Exec SQL 5 | select count(*) 6 | into :FailedCount INDICATOR :NFFlag 7 | from somelib/request a, somelib/response b 8 | where a.wasd = b.wasd 9 | and trans_date = :TodayTest 10 | and substring(trans_time, 1, 2) = :ThisHour; -------------------------------------------------------------------------------- /tests/issues/97.clle: -------------------------------------------------------------------------------- 1 | /* https://github.com/barrettotte/vscode-ibmi-languages/issues/97 */ 2 | 3 | CHGVAR VAR(&WRK_CYY#) VALUE(&CYY# + 1900) /* change + 4 | to ccyy */ 5 | CHGVAR VAR(&YEAR4) VALUE(&WRK_CYY#) 6 | #ERROR: 7 | RTVDTAARA DTAARA(PPA703/SOMELIB (1 2)) RTNVAR(&MO) 8 | RTVDTAARA DTAARA(PPA703/SOMELIB (15 4)) RTNVAR(&YR4) 9 | -------------------------------------------------------------------------------- /tests/general/test.icff: -------------------------------------------------------------------------------- 1 | A* ICF file example 2 | TEST A R SNDPASS 3 | A FLD1 18A 4 | A R CHKPASS 5 | A FLD1 1A 6 | WASD A* 7 | A R EVOKPGM 8 | A EVOKE(MYLIB/SOMEPGM) 9 | XXXXXA SECURITY(2 'PASSWRD' + 10 | A 3 'USRID') -------------------------------------------------------------------------------- /tests/issues/29.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/29 3 | // 4 | ctl-opt main(main); 5 | ctl-opt option(*srcstmt:*nodebugio:*nounref) dftactgrp(*no); 6 | ctl-opt datfmt(*iso) timfmt(*iso); 7 | 8 | dcl-pr main extpgm('TESTR') end-pr; 9 | 10 | dcl-proc main; 11 | dsply ('Hello world'); 12 | 13 | on-exit; 14 | *inlr = *on; 15 | return; 16 | end-proc; 17 | -------------------------------------------------------------------------------- /tests/issues/58.mi: -------------------------------------------------------------------------------- 1 | /* https://github.com/barrettotte/vscode-ibmi-languages/issues/58 */ 2 | 3 | TEST-1: 4 | CPYBLA IO-SRCLIB,OIR-SRCLIB 5 | 6 | TEST-2: 7 | CMPBLA(B) LIBNAM,'QTEMP '/EQ(TEMPLIB) 8 | 9 | /* Other random things that came up when messing around */ 10 | MISC: 11 | DCL SYSPTR CL06 INIT("CL06", TYPE(PGM)); /* comment after statement */ 12 | DCL OL CL06OL (USRSPC, OFFSET@) ARG; /* identifer ending in keyword */ 13 | -------------------------------------------------------------------------------- /tests/issues/104.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | dcl-ds *n; 4 | var1 int; 5 | var2 char samepos( var1 ); 6 | end-ds; 7 | 8 | dcl-pr format_date varchar(100); 9 | dateparm date(*iso) const; 10 | end-pr; 11 | dcl-pr retrieve_message varchar(100); 12 | msgid char(7) const; 13 | replacement_text varchar(100) const; 14 | end-pr; 15 | 16 | dcl-pr format varchar(100) overload(format_date : retrieve_message); 17 | 18 | dcl-s dueDate date nullind; 19 | -------------------------------------------------------------------------------- /tests/issues/48.rpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/48 2 | IXYZ123 AC 40 62 C4 3 | * a 4 | I OR 41 62 C5 5 | * b 6 | I OR 42 62 C6 7 | * c 8 | I OR 43 62 C7 9 | * d 10 | I OR 44 62 C8 11 | * e -------------------------------------------------------------------------------- /tests/issues/63.rpgle: -------------------------------------------------------------------------------- 1 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/63 2 | C* 3 | C FOR i = 1 to 6 by 2 4 | C FOR j = 1 to 2 5 | C myvar DSPLY 6 | C ENDFOR 7 | C ENDFOR 8 | for i = 1 to 6 by 2; 9 | for j = 1 to 2; 10 | dsply (myvar); 11 | endfor; 12 | endfor; -------------------------------------------------------------------------------- /dev/rpgle-fixed/rpgle-d.txt: -------------------------------------------------------------------------------- 1 | ZONED|VARYING|VARUCS2|VARGRAPH|VARCHAR|VALUE|UNS|UCS2|TOFILE|TIMFMT|TIMESTAMP|TIME|TEMPLATE|STATIC|RTNPARM|QUALIFIED|PSDS|PROCPTR|PREFIX|POS|POINTER|PERRCD|PACKEVEN|PACKED|OVERLAY|OPTIONS|OPDESC|OCCURS|OBJECT|NOOPT|LIKEREC|LIKEFILE|LIKEDS|LIKE|LEN|INZ|IND|INT|IMPORT|GRAPH|FROMFILE|FLOAT|EXTPROC|EXTPGM|EXTNAME|EXTFMT|EXTFLD|EXT|EXPORT|DTAARA|DIM|DESCEND|DATFMT|DATE|CTDATA|CONST|CLASS|CHAR|CCSID|BINDEC|BASED|ASCEND|ALTSEQ|ALT|ALIGN|ALIAS -------------------------------------------------------------------------------- /tests/issues/84.rpgle: -------------------------------------------------------------------------------- 1 | * Convert fields to external form 2 | C N30 3 | CANN27 EXSR MOCV#X 4 | C DOU W0HLP = 'N' 5 | C MOVEL 'N' W0HLP 6 | C MOVE *IN25 HELP25 7 | C MOVE *ALL'0' ##OFF 8 | C MOVEA ##OFF *IN(1) 9 | C MOVE HELP25 *IN25 -------------------------------------------------------------------------------- /dev/dds/prtf.txt: -------------------------------------------------------------------------------- 1 | ZFOLD|UNISCRIPT|UNDERLINE|TXTRTT|TRNSPY|TIMSEP|TIMFMT|TIME|TEXT|STRPAGGRP|STAPLE|SPACEB|SPACEA|SKIPB|SKIPA|RELPOS|REFFLD|REF|PRTQLTY|POSITION|PAGSEG|PAGRTT|PAGNBR|OVERLAY|OUTBIN|MSGCON|LPI|LINE|INVMMAP|INVDTAMAP|INDTXT|INDARA|HIGHLIGHT|GDF|FORCE|FONTNAME|FONT|FNTCHRSET|FLTPCN|FLTFIXDEC|ENDPAGGRP|ENDPAGE|EDTWRD|EDTCDE|DUPLEX|DTASTMCMD|DRAWER|DOCIDXTAG|DLTEDT|DFT|DFNCHR|DATSEP|DATFMT|DATE|CVTDTA|CPI|COLOR|CHRSIZ|CHRID|CDEFNT|BOX|BLKFOLD|BARCODE|ALIAS|AFPRSC -------------------------------------------------------------------------------- /dev/rpgle-free/rpgle-definition.txt: -------------------------------------------------------------------------------- 1 | ZONED|VARYING|VARUCS2|VARGRAPH|VARCHAR|VALUE|UNS|UCS2|TOFILE|TIMFMT|TIMESTAMP|TIME|TEMPLATE|STATIC|RTNPARM|QUALIFIED|PSDS|PROCPTR|PREFIX|POS|POINTER|PERRCD|PACKEVEN|PACKED|OVERLAY|OPTIONS|OPDESC|OCCURS|OBJECT|NOOPT|LIKEREC|LIKEFILE|LIKEDS|LIKE|LEN|INZ|IND|INT|IMPORT|GRAPH|FROMFILE|FLOAT|EXTPROC|EXTPGM|EXTNAME|EXTFMT|EXTFLD|EXT|EXPORT|DTAARA|DIM|DESCEND|DATFMT|DATE|CTDATA|CONST|CLASS|CHAR|CCSID|BINDEC|BASED|ASCEND|ALTSEQ|ALT|ALIGN|ALIAS -------------------------------------------------------------------------------- /tests/issues/80.rpgle: -------------------------------------------------------------------------------- 1 | ** COVERAGES ARRAY 2 | MED EXP 1 3 | INC LOSS 2 4 | FUN EXP 3 5 | ACC DEATH 4 6 | COMB-FPB 5 7 | PIP LIMIT 6 8 | DED/INCOME 7 9 | SEC 8 10 | PIP DED 9 11 | PIP 10 12 | DEDUCTIBLE 11 13 | DED/CO-ORD 12 -------------------------------------------------------------------------------- /dev/rpgle-fixed/rpgle-bif.txt: -------------------------------------------------------------------------------- 1 | YEARS|XML|XLATE|XFOOT|UNSH|UNS|UCS2|TRIMR|TRIML|TRIM|TLOOKUP|TIMESTAMP|TIME|THIS|SUBST|SUBDT|SUBARR|STR|STATUS|SQRT|SIZE|SHTDN|SECONDS|SCANRPL|SCAN|REPLACE|REM|REALLOC|PROC|PARSER|PARMNUM|PARMS|PADDR|OPEN|OCCUR|NULLIND|MSECONDS|MONTHS|MINUTES|MIN|MAX|LOOKUP|LEN|KDS|INTH|INT|HOURS|HANDLER|GRAPH|GEN|FOUND|FLOAT|FIELDS|ERROR|EQUAL|EOF|ELEM|EDITW|EDITFLT|EDITC|DIV|DIFF|DECPOS|DECH|DEC|DAYS|DATE|DATA|CHECKR|CHECK|CHAR|BITXOR|BITOR|BITNOT|BITAND|ALLOC|ADDR|ABS -------------------------------------------------------------------------------- /tests/issues/124.pnlgrp: -------------------------------------------------------------------------------- 1 | :panel name=main 2 | help='menu/main' 3 | keyl=small 4 | panelid=zmenu 5 | topsep=space 6 | .My Main Menu 7 | :menu depth='*'. 8 | :topinst.Select one of the following: 9 | :menui help=MNUSER 10 | option=1 11 | action='MENU X' 12 | .Display menu X 13 | :menui help=MNSYS 14 | option=2 15 | action='MENU SYSOPR' 16 | .System operations 17 | :mi help=MNOFF 18 | option=90 19 | action='CMD SIGNOFF' 20 | .Sign off 21 | :emenu. 22 | :cmdline size=long.Selection or command 23 | :epanel. 24 | -------------------------------------------------------------------------------- /tests/issues/141.pf: -------------------------------------------------------------------------------- 1 | A ACNAME 20A TEXT('text') 2 | A COLHDG('Column' + 3 | A 'Heading' ) 4 | A LONGFIELD R REF(ABC) 5 | A LONGFIELD2RXXXXXXXXXXXXXXXREF(ABC2) 6 | A LONGFIELD3R REF(ABC3) 7 | XXXXXA LONGFIELD4R REF(ABC4) 8 | XXXXXAXXXXXXXXXXXXLONGFIELD5R REF(ABC5) 9 | A* Keyfield level 10 | A K ACLEVELID 11 | -------------------------------------------------------------------------------- /tests/issues/52.rpgle: -------------------------------------------------------------------------------- 1 | H* https://github.com/barrettotte/vscode-ibmi-languages/issues/52 2 | H* 3 | YIKESH/TITLE Messing around with fixed and free format 4 | H* 5 | OH NO ctl-opt option(*srcstmt:*noDebugIO:*nounref) dftActGrp(*no); 6 | D* 7 | XXXXXDCvtScore S 10A 8 | dcl-s myvar char(1) inz('X'); 9 | 10 | exec SQL 11 | select * from someTable limit 1; 12 | -------------------------------------------------------------------------------- /tests/issues/66.sqlrpgle: -------------------------------------------------------------------------------- 1 | H* https://github.com/barrettotte/vscode-ibmi-languages/issues/66 2 | H* 3 | YIKESH/TITLE Messing around with fixed and free format 4 | H* 5 | OH NO ctl-opt option(*srcstmt:*noDebugIO:*nounref) dftActGrp(*no); 6 | D* 7 | XXXXXDCvtScore S 10A 8 | dcl-s myvar char(1) inz('X'); 9 | 10 | exec SQL 11 | select * from someTable limit 1; -------------------------------------------------------------------------------- /tests/issues/96.sqlrpgle: -------------------------------------------------------------------------------- 1 | C* https://github.com/barrettotte/vscode-ibmi-languages/issues/96 2 | C* 3 | C exsr DltClaims 4 | C exsr DltAr 5 | ///free 6 | // some commented out SQLRPGLE 7 | // exec sql select count(*) from QSYS2.SYSTABLES; 8 | ///end-free 9 | 10 | C IF POLTP2='PA' or POLTP2='AC' or 11 | C POLTP2='GP' 12 | * xxxxxxxxxxxxxxxxxxx 13 | C CALL 'PGM068' MyParms -------------------------------------------------------------------------------- /tests/issues/82.rpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/82 2 | * 3 | * fixed comment 4 | // free comment 5 | 6 | /FREE 7 | // comment in /FREE 8 | // oh...nice 9 | /END-FREE 10 | 11 | /if not defined (SMS) 12 | /define SMS 13 | 14 | dcl-ds smsRequest qualified template; 15 | phone_to varchar(16); 16 | phone_from varchar(16); 17 | msg varchar(1600); 18 | account varchar(64); 19 | auth varchar(64); 20 | end-ds; 21 | 22 | /endif 23 | -------------------------------------------------------------------------------- /tests/issues/106.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | snd-msg 'Hello World'; 4 | 5 | monitor; 6 | create_new_account (); 7 | on-excp 'ARV0203' : 'ARV0204'; 8 | // handle two ARV messages 9 | endmon; 10 | 11 | arv0203_reptext.badFile = filename; 12 | arv0203_reptext.badIdno = id_no; 13 | SND-MSG %MSG ('ARV0203' : 'ARVMSGS' : arv0203_reptext); 14 | 15 | // Send a message to the caller of our main procedure 16 | // - stack offset = 2 since the "caller" is actually the 17 | // PEP for the program 18 | SND-MSG *ESCAPE 'Unexpected customer type ' + type 19 | %TARGET('ARVMAIN' : 2); -------------------------------------------------------------------------------- /tests/issues/115.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/115 4 | 5 | dcl-ds custInfo qualified; 6 | id int(10); 7 | name varchar(50); 8 | city varchar(50); 9 | orders likeds(order_t) dim(100); 10 | numOrders int(10); 11 | end-ds custInfo; 12 | 13 | dcl-ds prtDs len(132) end-ds; 14 | 15 | dcl-ds *N; 16 | dcl-subf select char(10); // subfield has reserved word as name, dcl-subf required 17 | name char(10); // 18 | dcl-subf address char(25); // not required, still valid 19 | end-ds; 20 | -------------------------------------------------------------------------------- /.vscode/launch.json: -------------------------------------------------------------------------------- 1 | { 2 | // Use IntelliSense to learn about possible attributes. 3 | // Hover to view descriptions of existing attributes. 4 | // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 5 | "version": "0.2.0", 6 | "configurations": [ 7 | { 8 | "name" : "Extension", 9 | "type": "extensionHost", 10 | "request": "launch", 11 | "runtimeExecutable": "${execPath}", 12 | "args": [ 13 | "--extensionDevelopmentPath=${workspaceFolder}" 14 | ] 15 | } 16 | ] 17 | } -------------------------------------------------------------------------------- /configurations/dds.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"] 7 | ], 8 | // symbols that are auto closed when typing 9 | "autoClosingPairs": [ 10 | //["{", "}"], 11 | ["[", "]"], 12 | ["(", ")"], 13 | ["\"", "\""], 14 | ["'", "'"] 15 | ], 16 | // symbols that that can be used to surround a selection 17 | "surroundingPairs": [ 18 | ["{", "}"], 19 | ["[", "]"], 20 | ["(", ")"], 21 | ["\"", "\""], 22 | ["'", "'"] 23 | ] 24 | } -------------------------------------------------------------------------------- /tests/issues/83.rpgle: -------------------------------------------------------------------------------- 1 | // I think this was fixed "by accident" in issue 82 2 | 3 | begsr testSubr1; 4 | dcl-s x int(10) inz(*zero); 5 | 6 | /FREE 7 | dsply ('FREE!'); 8 | /END-FREE 9 | C ADD 1 X 10 | x += 1; 11 | /FREE 12 | x += 1; 13 | C ADD 1 X 14 | endsr; 15 | 16 | begsr testSubr2; 17 | dcl-s x int(10) inz(*zero); 18 | C ADD 1 X 19 | // previous FREE directive should've been closed 20 | // at end of testSubr1 21 | endsr; -------------------------------------------------------------------------------- /tests/issues/52.pf: -------------------------------------------------------------------------------- 1 | A* https://github.com/barrettotte/vscode-ibmi-languages/issues/52 2 | A* 3 | A 4 | TEST A UNIQUE 5 | A R ACCOUNT TEXT('Record format text') 6 | A ACCOUNTNUM 12P 0 TEXT('text') 7 | A ACCURRENCY 3A TEXT('text') 8 | WASD A ACNAME 20A TEXT('* TESTING...') 9 | A 10 | AHHHHA COLHDG('Column' + 11 | A 'Heading' ) 12 | A* Keys 13 | A K ACCOUNTNUM 14 | A K ACCURRENCY -------------------------------------------------------------------------------- /tests/issues/102.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/102 3 | 4 | if PRPLPR.Rcenrldays > 0 and Ee_Days >= PRPLPR.Rcenrldays; 5 | if PRPLPR.Rcenrlamt > 0; 6 | exec sql select 'Y' into :Eligible 7 | from PRPELVTB 8 | where ELEMP = :Empid and ELTYPE in ( 'X' ) 9 | and ELLPID = :Leaveplanid and ELEFFDATE <= :Dates.Annv_Earned_Nxt 10 | -- ... 11 | order by ELEFFDATE desc 12 | fetch first 1 rows only; 13 | return Eligible; 14 | else; 15 | return 'Y'; 16 | endif; 17 | elseif PRPLPR.Rcenrldays > 0 and Ee_Days < PRPLPR.Rcenrldays; 18 | return 'N'; 19 | else; 20 | return 'Y'; 21 | endif 22 | -------------------------------------------------------------------------------- /dev/cl/util.py: -------------------------------------------------------------------------------- 1 | # copy contents from https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/clfinder/finder30.htm into ops.txt 2 | # ordered in reverse so commands like WRKLIB don't get matched before WRKLIBPDM 3 | i = 0 4 | opgroups = [] 5 | with open('ops.txt', 'r') as f: 6 | ops = [] 7 | for line in f: 8 | ops.append(line.strip().split(' ')[0]) 9 | i += 1 10 | if i == 100: 11 | opgroups.append('{"name": "keyword.other.cl", "match": "(?i)\\\\b(' + '|'.join(sorted(ops, reverse=True)) + ')\\\\b"}') 12 | ops = [] 13 | i = 0 14 | with open('regex.json', 'w') as f: 15 | f.write('[' + (',\n'.join(sorted(opgroups, reverse=True))) + ']') -------------------------------------------------------------------------------- /tests/general/test2.dspf: -------------------------------------------------------------------------------- 1 | A* Test display file 2 | * 3 | AAN01n02n03R RECORD1 R12345J99B123654CF03(03 'EXIT') 4 | A R #SFLRCD TEXT('* TESTING...') 5 | 6 | A N79N31 DSPATR(UL) 7 | A N31 DSPATR(HI) 8 | A N25 OVRATR 9 | * 10 | A* Test identifier with a keyword in it 11 | WASD A #1LOCK 8 4'Lock Status:' 12 | * 13 | XXXXXA* Numeric constant at end of identifier 14 | AHHHHA #CBX#3 15 | * 16 | TEST A* Identifier with max width 17 | A R ABCDEFGHIJ CF03(03 'EXIT') 18 | -------------------------------------------------------------------------------- /configurations/mi.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"] 7 | ], 8 | // symbols that are auto closed when typing 9 | "autoClosingPairs": [ 10 | //["{", "}"], 11 | ["[", "]"], 12 | ["(", ")"], 13 | ["\"", "\""], 14 | ["'", "'"] 15 | ], 16 | // symbols that that can be used to surround a selection 17 | "surroundingPairs": [ 18 | ["{", "}"], 19 | ["[", "]"], 20 | ["(", ")"], 21 | ["\"", "\""], 22 | ["'", "'"] 23 | ], 24 | "comments": { 25 | "blockComment": ["/*", "*/"] 26 | } 27 | } -------------------------------------------------------------------------------- /dev/rpgle-fixed/rpgle-c.txt: -------------------------------------------------------------------------------- 1 | Z-SUB|Z-ADD|XML-SAX|XML-INTO|XLATE|XFOOT|WRITE|WHEN|UPDATE|UNLOCK|TIME|TESTZ|TESTN|TESTB|TEST|TAG|SUBST|SUBDUR|SUB|SQRT|SORTA|SND-MSG|SHTDN|SETON|SETOFF|SETLL|SETGT|SELECT|SCAN|ROLBK|RETURN|RESET|REL|REALLOC|READPE|READP|READE|READC|READ|POST|PLIST|PARM|OUT|OTHER|OR|OPEN|ON-EXIT|ON-EXCP|ON-ERROR|OCCUR|NEXT|MVR|MULT|MOVEL|MOVEA|MOVE|MONITOR|MLLZO|MLHZO|MHLZO|MHHZO|LOOKUP|LEAVESR|LEAVE|KLIST|KFLD|ITER|IN|IF|GOTO|FORCE|FOR|FEOD|EXTRCT|EXSR|EXFMT|EXCEPT|EVAL-CORR|EVALR|EVAL|ENDSL|ENDMON|ENDIF|ENDFOR|ENDDO|ENDCS|END|ELSEIF|ELSE|DUMP|DSPLY|DOW|DOU|DO|DIV|DELETE|DEFINE|DEALLOC|DATA-INTO|DATA-GEN|COMP|COMMIT|CLOSE|CLEAR|CHECKR|CHECK|CHAIN|CAT|CAS|CALLP|CALLB|CALL|CAB|BITON|BITOFF|BEGSR|AND|ALLOC|ADDUR|ADD|ACQ -------------------------------------------------------------------------------- /tests/issues/116.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // Control option keywords CHARCOUNTTYPES and CHARCOUNT 4 | 5 | ctl-opt charcounttypes(*utf8); 6 | ctl-opt charcount(*natural); 7 | 8 | // File definition keyword CHARCOUNT 9 | 10 | dcl-f filename charcount(*natural); 11 | 12 | // BIF %CHARCOUNT 13 | 14 | n = %charcount(string); 15 | 16 | // /CHARCOUNT directive 17 | 18 | /charcount natural 19 | /charcount stdcharsize 20 | 21 | // %SUBST keywords *NATURAL and *STDCHARSIZE 22 | 23 | string2 = %subst(string : 1 : 3 : *natural); 24 | string2 = %subst(string : 1 : 3 : *stdcharsize); 25 | 26 | // %CONCAT and %CONCATARR 27 | 28 | string = %concat(', ' : 'Cow' : 'Moon' : 'Dish' : 'Spoon'); 29 | string = %concatarr(':' : array); -------------------------------------------------------------------------------- /configurations/pnlgrp.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"] 7 | ], 8 | // symbols that are auto closed when typing 9 | "autoClosingPairs": [ 10 | ["{", "}"], 11 | ["[", "]"], 12 | ["(", ")"], 13 | ["\"", "\""], 14 | ["'", "'"], 15 | [/*, */] 16 | ], 17 | // symbols that that can be used to surround a selection 18 | "surroundingPairs": [ 19 | ["{", "}"], 20 | ["[", "]"], 21 | ["(", ")"], 22 | ["\"", "\""], 23 | ["'", "'"] 24 | ], 25 | "comments": { 26 | "lineComment": ".*" 27 | } 28 | } -------------------------------------------------------------------------------- /configurations/cl.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"] 7 | ], 8 | // symbols that are auto closed when typing 9 | "autoClosingPairs": [ 10 | ["{", "}"], 11 | ["[", "]"], 12 | ["(", ")"], 13 | ["\"", "\""], 14 | ["'", "'"], 15 | [/*, */] 16 | ], 17 | // symbols that that can be used to surround a selection 18 | "surroundingPairs": [ 19 | ["{", "}"], 20 | ["[", "]"], 21 | ["(", ")"], 22 | ["\"", "\""], 23 | ["'", "'"] 24 | ], 25 | "comments": { 26 | "blockComment": ["/*", "*/"] 27 | } 28 | } -------------------------------------------------------------------------------- /configurations/cmd.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"] 7 | ], 8 | // symbols that are auto closed when typing 9 | "autoClosingPairs": [ 10 | ["{", "}"], 11 | ["[", "]"], 12 | ["(", ")"], 13 | ["\"", "\""], 14 | ["'", "'"], 15 | [/*, */] 16 | ], 17 | // symbols that that can be used to surround a selection 18 | "surroundingPairs": [ 19 | ["{", "}"], 20 | ["[", "]"], 21 | ["(", ")"], 22 | ["\"", "\""], 23 | ["'", "'"] 24 | ], 25 | "comments": { 26 | "blockComment": ["/*", "*/"] 27 | } 28 | } -------------------------------------------------------------------------------- /tests/issues/91.sqlrpgle: -------------------------------------------------------------------------------- 1 | EXEC SQL 2 | DECLARE CSR CURSOR FOR 3 | SELECT * FROM SOME_TABLE 4 | WHERE (RMPCDE > :X@PCDE 5 | OR (RMPCDE = :X@PCDE AND 6 | RMCRIT > :X@CRIT ) 7 | OR (RMPCDE = :X@PCDE AND 8 | RMCRIT = :X@CRIT AND 9 | RMSQ## >= :X@SQ## ) 10 | ) 11 | ORDER BY RMPCDE ASC, 12 | RMCRIT ASC, 13 | RMSQ## ASC; 14 | EXEC SQL 15 | OPEN CSR; 16 | -------------------------------------------------------------------------------- /tests/issues/101.sqlrpgle: -------------------------------------------------------------------------------- 1 | /free 2 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/101 3 | 4 | MySQLStmt = ' with + 5 | P+ 6 | new line added + 7 | duplicate of above + 8 | another line added - 9 | another duplication of above - 10 | )'; 11 | /end-free 12 | 13 | d* bug introduced in https://github.com/barrettotte/vscode-ibmi-languages/issues/23 14 | davlchr c 'ABCDEFGHIJKLMNOPQRSTUVWXYZ- 15 | d abcdefghijklmnopqrstuvwxyz- 16 | d АБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ- 17 | d абвгдеёжзийклмнопрстуфхцчшщъыьэюя- 18 | d 1234567890\ ' 19 | -------------------------------------------------------------------------------- /tests/issues/34.rpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/34 2 | ,* *INZSR 3 | C ENDSR *INZSR 4 | /EJECT TPBFVR 5 | /COPY EQCPYLESRC,PSSR_B Program error control sub (on-line) IL EQTPBFVR 6 | /EJECT TPBFVR 7 | /COPY EQCPYLESRC,NUMEDT Edit number without leading zeros C EQTPBFVR 8 | ,*---------------------------------------------------------------------------------------TPBFVR 9 | -------------------------------------------------------------------------------- /tests/issues/23.rpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/24 2 | * 3 | davlchr c 'ABCDEFGHIJKLMNOPQRSTUVWXYZ- 4 | d abcdefghijklmnopqrstuvwxyz- 5 | d АБВГДЕЁЖЗИЙКЛМНОПРСТУФХЦЧШЩЪЫЬЭЮЯ- 6 | d абвгдеёжзийклмнопрстуфхцчшщъыьэюя- 7 | d 1234567890\ ' 8 | * 9 | * Notes: 10 | * - Remove string escape highlighting in each file type 11 | * - End string match regex at newline instead of ' 12 | * OR highlight specs on new line and assume string for the rest of the line? 13 | * - However you fix this can be applied to DDS regex as well... 14 | -------------------------------------------------------------------------------- /tests/issues/125.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // Parameter built-in functions %PASSED and %OMITTED 4 | 5 | // p1 is required, but *OMIT could be passed 6 | if %passed(p1); 7 | dsply ('Parameter p1 = ' + %char(p1)); 8 | elseif %omitted(p1); 9 | dsply ('*OMIT was passed for parameter p1'); 10 | else; 11 | snd-msg *escape 'p1 is a required parameter but ' 12 | + 'no parameter was passed'; 13 | endif; 14 | 15 | // SELECT statement with an operand 16 | 17 | select i + 1; 18 | when-in %list(1 : 3 : 5 : 7); 19 | dsply ('i+1 is one of 3, 5, 5, 7 ... i = ' + %char(i)); 20 | when-is n; 21 | dsply ('i+1 = n, so this block is chosen ... n = ' + %char(n)); 22 | when-in arr1; 23 | dsply ('i+1 is equal to an element of arr1 ' + %char(i)); 24 | other; 25 | dsply ('i+1 has some other value'); 26 | endsl; 27 | -------------------------------------------------------------------------------- /tests/issues/93.sqlrpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/93 2 | * 3 | C NameTif BEGSR 4 | * Determine IR image name 5 | C EXSR POP Get next number 6 | C MOVE 'UNDR' @IRDRW 4 7 | CSR POP BEGSR 8 | * 9 | C* Pop next tif file number from the queue 10 | C CALL 'ARRT511A' 11 | C PARM RTRN 7 12 | C PARM 'TIF' TYPE 3 13 | C PARM NXTTIF 9 0 14 | C MOVEL NXTTIF UNIQUE 10 15 | C ENDSR 16 | *-------------------------DefineCursor 17 | C DefineCursor BEGSR -------------------------------------------------------------------------------- /tests/issues/114.rpgle: -------------------------------------------------------------------------------- 1 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/114 2 | * 3 | /copy qrpglesrc,cpy_good 4 | c/copy qrpglesrc,cpy_good 5 | d/copy qrpglesrc,cpy_bad 6 | * 7 | /include qrpglesrc,inc_good 8 | c/include qrpglesrc,inc_good 9 | d/include qrpglesrc,inc_bad 10 | 11 | * fixing up another bug I saw in 34.rpgle, TPBFVR should be commented 12 | C ENDSR *INZSR 13 | /EJECT TPBFVR 14 | /COPY EQCPYLESRC,PSSR_B Program error control sub (on-line) IL EQTPBFVR 15 | C/EJECT TPBFVR 16 | /COPY EQCPYLESRC,NUMEDT Edit number without leading zeros C EQTPBFVR -------------------------------------------------------------------------------- /tests/issues/59.sqlrpgle: -------------------------------------------------------------------------------- 1 | H* https://github.com/barrettotte/vscode-ibmi-languages/issues/59 2 | C* 3 | C* Embedded SQL fixed form 4 | C/EXEC SQL 5 | C* fixed-format comment 6 | C+ DECLARE MYCSR CURSOR FOR 7 | C+ SELECT * FROM SOMETABLE 8 | C+ WHERE (COLUMNA = :COLUMNA 9 | C+ AND COLUMNB = :COLUMNB 10 | C+ ) 11 | C+ ORDER BY COLUMNA ASC, 12 | C+ COLUMNB ASC 13 | xxxx C+ -- SQL comment 14 | C/END-EXEC 15 | C* 16 | XXXXXC/EXEC SQL 17 | C+ OPEN MYCSR 18 | xx C/END-EXEC 19 | C* 20 | xxxxxC IF SQLCOD = -502 21 | C/EXEC SQL 22 | C+ CLOSE MYCSR 23 | C/END-EXEC 24 | C ELSE 25 | C IF SQLCOD < 0 26 | C EXSR MYSUBR 27 | C ENDIF 28 | C ENDIF -------------------------------------------------------------------------------- /.github/workflows/main.yml: -------------------------------------------------------------------------------- 1 | on: 2 | release: 3 | types: [created] 4 | workflow_dispatch: 5 | 6 | jobs: 7 | release: 8 | name: Release and publish 9 | runs-on: ubuntu-latest 10 | 11 | steps: 12 | - uses: actions/checkout@v4 13 | - run: npm install 14 | 15 | - uses: actions/setup-node@v4 16 | with: 17 | node-version: 20 18 | registry-url: https://registry.npmjs.org/ 19 | 20 | - name: Install the dependencies 21 | run: npm i 22 | 23 | - name: Install vsce and Open VSX 24 | run: npm i -g @vscode/vsce ovsx 25 | 26 | - name: Publish to VS Code Marketplace 27 | id: pub_vsce 28 | continue-on-error: true 29 | run: | 30 | vsce publish -p ${{ secrets.VSCE_TOKEN }} 31 | 32 | - name: Publish to Open VSX 33 | continue-on-error: true 34 | id: pub_ovsx 35 | run: | 36 | npx ovsx publish -p ${{ secrets.OPEN_VSX }} 37 | -------------------------------------------------------------------------------- /dev/rpg400/ops.txt: -------------------------------------------------------------------------------- 1 | ACQ 2 | ADD 3 | AND 4 | BEGSR 5 | BITOF 6 | BITON 7 | CAB 8 | CALL 9 | CAS 10 | CAT 11 | CHAIN 12 | CHECK 13 | CHEKR 14 | CLEAR 15 | CLOSE 16 | COMIT 17 | COMP 18 | DEBUG 19 | DEFN 20 | DELET 21 | DIV 22 | DO 23 | DOU 24 | DOW 25 | DSPLY 26 | DUMP 27 | ELSE 28 | END 29 | ENDSR 30 | EXCPT 31 | EXFMT 32 | EXSR 33 | FEOD 34 | FORCE 35 | FREE 36 | GOTO 37 | IF 38 | IN 39 | ITER 40 | KFLD 41 | KLIST 42 | LEAVE 43 | LOKUP 44 | MHHZO 45 | MHLZO 46 | MLHZO 47 | MLLZO 48 | MOVE 49 | MOVEA 50 | MOVEL 51 | MULT 52 | MVR 53 | NEXT 54 | OCUR 55 | OPEN 56 | OR 57 | OTHER 58 | OUT 59 | PARM 60 | PLIST 61 | POST 62 | READ 63 | READC 64 | READE 65 | READP 66 | REDPE 67 | REL 68 | RESET 69 | RETRN 70 | ROLBK 71 | SCAN 72 | SELEC 73 | SETGT 74 | SETLL 75 | SETOF 76 | SETON 77 | SHTDN 78 | SORTA 79 | SQRT 80 | SUB 81 | SUBST 82 | TAG 83 | TESTB 84 | TESTN 85 | TESTZ 86 | TIME 87 | UNLCK 88 | UPDAT 89 | WH 90 | WRITE 91 | XFOOT 92 | XLATE 93 | Z-ADD 94 | Z-SUB -------------------------------------------------------------------------------- /tests/general/test.pf: -------------------------------------------------------------------------------- 1 | A* Testing a physical file 2 | A* 3 | A* Modified DDS from 4 | A* http://www.go4as400.com/Source-physical-file-and-logical-file-in-as400/files.aspx?cid=4 5 | A 6 | A* File level 7 | A UNIQUE 8 | A* Record format level 9 | A R ACCOUNT TEXT('Record format text') 10 | A* Field level 11 | A ACLEVELID 2P 0 TEXT('text') 12 | A ACORGCOD 3P 0 TEXT('text') 13 | A ACCOUNTNUM 12P 0 TEXT('text') 14 | A ACCURRENCY 3A TEXT('text') 15 | A ACNAME 20A TEXT('text') 16 | A COLHDG('Column' + 17 | A 'Heading' ) 18 | A* Keyfield level 19 | A K ACLEVELID 20 | A K ACORGCOD 21 | A K ACCOUNTNUM 22 | A K ACCURRENCY 23 | A* -------------------------------------------------------------------------------- /tests/general/test-cl-comments.clle: -------------------------------------------------------------------------------- 1 | pgm 2 | 3 | dcl &test *char 10 4 | /*Is this a comment? Yes*/dcl &varA *char 1 5 | /*Is this a comment? Yes*/dcl &varB *char 1 6 | /* Is this a comment? Yes*/dcl &varC *char 1 7 | /**Is this a comment? Yes*/dcl &varD *char 1 8 | LABEL1:/*Is this a comment? NO, compile will fail!*/ 9 | LABEL2: /*Is this a comment? Yes*/ 10 | LABEL3:/**Is this a comment? Yes*/ 11 | 12 | chgvar &test ( '/* Is this a comment? No, it is a string */' ) 13 | 14 | chgvar &test/* Is this a comment? Yes */( 'text' ) 15 | 16 | /*Is this a comment?*/chgvar &test 'a' 17 | /*Is this a comment?*/chgvar &test 'a' 18 | chgvar/*Is this a comment? NO, compile will fail!*/&test 'a' 19 | chgvar /*Is this a comment? Yes*/&test 'a' 20 | chgvar /**Is this a comment? Yes*/&test 'a' 21 | chgvar /*Is this a comment? &test 'a' + 22 | Yes*/&test 'a' 23 | 24 | /* Is *ALL identified as special value and not start of comment? Yes*/ 25 | dspobjd obj(&test/*ALL) objtype(*file) output(*outfile) outfile(qtemp/objects) + 26 | /* vscode comment fix */ 27 | 28 | endpgm -------------------------------------------------------------------------------- /tests/issues/78.rpgle: -------------------------------------------------------------------------------- 1 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/78 2 | * 3 | * Define LARGE_FILES to get 64-bit version 4 | 5 | /IF DEFINED(QIBM_IFS_INCLUDED) 6 | /EOF 7 | /ENDIF 8 | /DEFINE QIBM_IFS_INCLUDED 9 | 10 | /COPY QSYSINC/QRPGLESRC,SYSTYPES 11 | /COPY QSYSINC/QRPGLESRC,SYSSTAT 12 | /COPY QSYSINC/QRPGLESRC,FCNTL 13 | /COPY QSYSINC/QRPGLESRC,UNISTD 14 | /COPY QSYSINC/QRPGLESRC,ERRNO 15 | 16 | D STREAM_NEW_LINE... xxxxxx 17 | D C X'15' 18 | 19 | D STREAM_LINE_FEED... 20 | D C X'25' 21 | 22 | D STREAM_CARRIAGE_RETURN... 23 | D C X'0D' 24 | 25 | * ... 26 | * 27 | * Notes: 28 | * this is an example of a "DX" prompt 29 | * I think its triggered via '...' 30 | * 31 | * Prompt: 32 | * Name - size 74 33 | * Comment - size 20 34 | -------------------------------------------------------------------------------- /tests/general/test.prtf: -------------------------------------------------------------------------------- 1 | A INDARA 2 | A REF(TESTPRTF) 3 | WASD A R PRHEADER 4 | A PROGRAM 10A 1SKIPB(001) 5 | A USER 10A +1 6 | A 56'MY REPORT' 7 | A 113TIME 8 | A +1DATE(*YY) 9 | A EDTCDE(Y) 10 | XXXXXA* 11 | A 1'ID' 12 | TEST A HIGHLIGHT 13 | A UNDERLINE 14 | A SPACEB(001) 15 | A +1'DESCRIPTION' 16 | A HIGHLIGHT 17 | A UNDERLINE 18 | A 123'Page' 19 | A +1PAGNBR 20 | A EDTCDE(Z) -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2020 Barrett Otte 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. -------------------------------------------------------------------------------- /tests/issues/110.rpgle: -------------------------------------------------------------------------------- 1 | D* https://github.com/barrettotte/vscode-ibmi-languages/issues/110 2 | * 3 | D D_SPEC C 'D' 4 | D CL_START C Const('SEQNBR *...+... 1 ...+... 2') 5 | D CL_END C Const('E N D O F S O U R C E') 6 | D* 7 | D* error caused by extended names in D spec 8 | D* 9 | D STREAM_NEW_LINE... xxxxxx 10 | D C X'15' 11 | D EVEN... awdasasdasd 12 | D C X'15' 13 | D ODD... asdasdasd 14 | D C X'15' 15 | D STREAM_NEW_LINX... xxxxxx 16 | D C X'15' 17 | D STREAM_LINE_FEED... 18 | D C X'25' 19 | D STREAM_CARRIAGE_RETURN... 20 | D C X'0D' -------------------------------------------------------------------------------- /tests/issues/60.rpgle: -------------------------------------------------------------------------------- 1 | 2 | H* https://github.com/barrettotte/vscode-ibmi-languages/issues/60 3 | * 4 | ***** Case One ***** 5 | 10011 * Don't write Audit for GetMemberAttendanceList unless logging is on 6 | 10011C if e#wsName <> 'GetMemberAttendanceList' 7 | 10011C or (e#wsName = 'GetMemberAttendanceList' 8 | 10011C and loge00 = 'Y') 9 | C 10 | C clear *all tc023r 11 | C eval user23 = userid 12 | C eval pgmd23 = prognm 13 | C* 14 | C* 15 | C* 16 | C* 17 | C***** Case Two ***** 18 | z3319C* Frontend uses counts to control loop by don't count for 19 | z3319 * Moved here as the.... 20 | z3319 * and p#total were reset incorrectly 21 | z3319C if %eof(py015l4) 22 | z3319C eval p#last = p#totl 23 | z3319C else 24 | z3319C eval p#last = p#total - 1 25 | z3319C endif 26 | endif; 27 | endsr; 28 | /end-free 29 | z0200 ***************************************************** -------------------------------------------------------------------------------- /tests/issues/120.rpgle: -------------------------------------------------------------------------------- 1 | ****************************** 2 | * https://github.com/barrettotte/vscode-ibmi-languages/issues/120 3 | * 4 | * 5 | *************************************** 6 | // 7 | // test 8 | // 9 | //************************************ 10 | ctl-opt NoMain; 11 | 12 | /copy *LIBL/QptypeSrc,Sla2upr 13 | 14 | dcl-s ArraySize int(10) inz(500); 15 | dcl-ds CntryArray Qualified Dim(500); 16 | dcl-subf Code char(4); 17 | dcl-subf Country char(30); 18 | end-ds; 19 | 20 | dcl-ds StateArray Qualified Dim(500); 21 | dcl-subf CrCode char(4); 22 | dcl-Subf StCode char(2); 23 | end-ds; 24 | 25 | // test compile time array 26 | ** COVERAGES ARRAY 27 | MED EXP 1 28 | INC LOSS 2 29 | FUN EXP 3 30 | ACC DEATH 4 31 | COMB-FPB 5 32 | PIP LIMIT 6 33 | DED/INCOME 7 34 | SEC 8 35 | PIP DED 9 36 | PIP 10 37 | DEDUCTIBLE 11 38 | DED/CO-ORD 12 39 | -------------------------------------------------------------------------------- /tests/issues/132.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // %LEFT 4 | 5 | // Built-in function %LEFT(parameter_name) returns the leftmost characters in a string. 6 | 7 | dcl-s string char(10) inz('abcdefghij'); 8 | dcl-s string2 varchar(10); 9 | 10 | string2 = %LEFT(string : 3); 11 | // string2 = "abc" 12 | 13 | // %RIGHT 14 | 15 | // Built-in function %RIGHT(parameter_name) returns the rightmost characters in a string. 16 | 17 | dcl-s string char(10) inz('abcdefghij'); 18 | dcl-s string2 varchar(10); 19 | 20 | string2 = %RIGHT(string : 3); 21 | // string2 = "hij" 22 | 23 | // ENUMERATION 24 | 25 | // Defining an enumeration 26 | 27 | dcl-enum colorCodes qualified; 28 | blue 1; 29 | green 2; 30 | yellow 3; 31 | end-enum; 32 | 33 | dcl-enum boolean; 34 | true '1'; 35 | false '0'; 36 | end-enum; 37 | 38 | dcl-enum nameSize qualified; 39 | system 10; 40 | path 5000; 41 | dcl-c dsply 52; // Name "DSPLY" needs DCL-C 42 | end-enum; 43 | 44 | dcl-s ifsFile varchar(nameSize.path); // Use the enum value in a definition 45 | 46 | dcl-s color int(10); 47 | dcl-s isValid ind; 48 | 49 | color = colorCodes.blue; // Use the qualified enum value 50 | isValid = true; // Use the unqualified enum value 51 | 52 | -------------------------------------------------------------------------------- /dev/dds/dspf.txt: -------------------------------------------------------------------------------- 1 | WRDWRAP|WINDOW|WDWTITLE|WDWBORDER|VLDCMDKEY|VALUES|VALNUM|USRRSTDSP|USRDSPMGT|USRDFN|USER|UNLOCK|TIMSEP|TIMFMT|TIME|TEXT|SYSNAME|SNGCHCFLD|SLNO|SFLSNGCHC|SFLSIZ|SFLSCROLL|SFLRTNSEL|SFLROLVAL|SFLRNA|SFLRCDNBR|SFLPGMQ|SFLPAG|SFLNXTCHG|SFLMSGRCD|SFLMSGKEY|SFLMSG|SFLMODE|SFLMLTCHC|SFLLIN|SFLINZ|SFLFOLD|SFLENTER|SFLEND|SFLDSPCTL|SFLDSP|SFLDROP|SFLDLT|SFLCTL|SFLCSRRRN|SFLCSRPRG|SFLCLR|SFLCHCCTL|SFL|SETOFF|SETOF|RTNDTA|RTNCSRLOC|ROLLUP|ROLLDOWN|RMVWDW|RETLCKSTS|RETKEY|REFFLD|REF|RANGE|PUTRETAIN|PUTOVR|PULLDOWN|PSHBTNFLD|PSHBTNCHC|PROTECT|PRINT|PASSRCD|PAGEDOWN|PAGEUP|OVRDTA|OVRATR|OVERLAY|OPENPRT|NOCCSID|MSGLOC|MSGID|MSGCON|MSGALARM|MOUBTN|MNUCNL|MNUBARSW|MNUBARSEP|MNUBARDSP|MNUBARCHC|MNUBAR|MLTCHFLD|MDTOFF|MAPVAL|LOWER|LOGOUT|LOGINP|LOCK|KEEP|INZRCD|INZINP|INVITE|INDTXT|INDARA|HTML|HOME|HLPTITLE|HLPSEQ|HLPSCHIDX|HLPRTN|HLPRCD|HLPPNLGRP|HLPID|HLPFULL|HLPEXCLD|HLPDOC|HLPCMDKEY|HLPCLR|HLPBDY|HLPARA|HELP|GETRETAIN|FRCDTA|FLTPCN|FLTFIXDEC|FLDCSRPRG|ERRSFL|ERRMSG|ERRMSGID|ERASEINP|ERASE|ENTFLDATR|EDTWRD|EDTMSK|EDTCDE|DUP|DSPSIZ|DSPRL|DSPMOD|DSPATR|DLTEDT|DLTCHK|DFTVAL|DFT|DATSEP|DATFMT|DATE|CSRLOC|CSRINPONLY|COMP|COLOR|CNTFLD|CMP|CLRL|CLEAR|CHRID|CHOICE|CHKMSGID|CHGINPDFT|CHECK|CHCUNAVAIL|CHCSLT|CHCCTL|CHCAVAIL|CHCACCEL|CHANGE|BLKFOLD|BLINK|BLANKS|AUTO|ASSUME|ALWROL|ALWGPH|ALTPAGEDWN|ALTPAGEUP|ALTNAME|ALTHELP|ALIAS|ALARM -------------------------------------------------------------------------------- /tests/issues/61.rpgle: -------------------------------------------------------------------------------- 1 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/61 2 | // 3 | C******************************* 4 | C FOR i = 1 to 6 by 2 5 | C FOR j = 1 to 2 6 | C myvar DSPLY 7 | C ENDFOR 8 | C ENDFOR 9 | for i = 1 to 6 by 2; 10 | for j = 1 to 2; 11 | dsply (myvar); 12 | endfor; 13 | endfor; 14 | C******************************* 15 | C 1 DO 10 16 | C 1 DO 3 17 | C myvar DSPLY 18 | C ENDDO 19 | C ENDDO 20 | C* 21 | C 1 DOW 5 22 | C 1 DO 2 23 | C myvar DSPLY 24 | C ENDDO 25 | C ENDDO 26 | C******************************* 27 | C* IFs 28 | C IF *IN12=*ON 29 | C IF *IN13=*OFF 30 | C myvar DSPLY 31 | C ELSE 32 | C myvar DSPLY 33 | C ENDIF 34 | C ELSE 35 | C myvar DSPLY 36 | C ENDIF -------------------------------------------------------------------------------- /tests/general/test1.mi: -------------------------------------------------------------------------------- 1 | /********************************************************************/ 2 | /* */ 3 | /* Program Name: MI01 */ 4 | /* Programming Language: MI */ 5 | /* Description: Return the larger of two packed arguments. */ 6 | /* */ 7 | /* From: https://www.ibm.com/support/knowledgecenter */ 8 | /* /en/ssw_ibm_i_73/rzatk/MIwritprog.htm */ 9 | /********************************************************************/ 10 | ENTRY * (PARM_LIST) EXT; 11 | DCL SPCPTR ARG1@ PARM; 12 | DCL SPCPTR ARG2@ PARM; 13 | DCL SPCPTR RESULT@ PARM; 14 | DCL OL PARM_LIST 15 | (ARG1@, 16 | ARG2@, 17 | RESULT@) 18 | PARM EXT; 19 | DCL DD ARG1 PKD(15,5) BAS(ARG1@); 20 | DCL DD ARG2 PKD(15,5) BAS(ARG2@); 21 | DCL DD RESULT PKD(15,5) BAS(RESULT@); 22 | CMPNV(B) ARG1,ARG2 / LO(ITS2); 23 | CPYNV RESULT,ARG1; 24 | B RETURN; 25 | ITS2: CPYNV RESULT,ARG2; 26 | RETURN: RTX *; 27 | PEND; -------------------------------------------------------------------------------- /tests/issues/40.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | /if not defined (SMS) 4 | /define SMS 5 | 6 | dcl-ds smsResponse qualified template; 7 | sid varchar(64); 8 | date_created varchar(64); 9 | date_updated varchar(64); 10 | date_sent varchar(64); 11 | account_sid varchar(64); 12 | phone_to varchar(32); 13 | phone_from varchar(32); 14 | msg_srv_sid varchar(64); 15 | body varchar(1600); 16 | status varchar(16); 17 | num_segments varchar(8); 18 | num_media varchar(8); 19 | direction varchar(32); 20 | api_version varchar(16); 21 | price varchar(8); 22 | price_unit varchar(4); 23 | error_code varchar(8); 24 | error_message varchar(512); 25 | uri varchar(256); 26 | end-ds; 27 | 28 | 29 | dcl-ds smsRequest qualified template; 30 | phone_to varchar(16); 31 | phone_from varchar(16); 32 | msg varchar(1600); 33 | account varchar(64); 34 | auth varchar(64); 35 | end-ds; 36 | 37 | 38 | // Send request DS to Twilio API, log and return entire response as DS 39 | dcl-pr sendSmsVerbose likeds(smsResponse); 40 | req likeds(smsRequest); 41 | end-pr; 42 | 43 | 44 | // Send request to Twilio API, log and only return error code 45 | // For simple requests where we don't care about the details immediately. 46 | // We just care whether it successfully sent the request 47 | dcl-pr sendSms varchar(8); 48 | phone_to varchar(16); 49 | phone_from varchar(16); 50 | msg varchar(1600); 51 | account varchar(64); 52 | auth varchar(64); 53 | end-pr; 54 | 55 | 56 | /endif -------------------------------------------------------------------------------- /tests/issues/150.dspf: -------------------------------------------------------------------------------- 1 | DSPSIZ(24 80 *DS3) 2 | CF12(12 'Cancel') 3 | R ASSUME 4 | ASSUME 5 | 1 2' ' 6 | R SF SFL 7 | SCRSHT 8A O 2 1 8 | COLOR(PNK) 9 | SCRLNG 30A O 2 12 10 | COLOR(PNK) 11 | R SFCTL SFLCTL(SF) 12 | SFLCSRRRN(&REC) 13 | 30 SFLDSP 14 | SFLDSPCTL 15 | 32 SFLEND(*MORE) 16 | SFLSIZ(12) 17 | SFLPAG(11) 18 | WINDOW(WINDOW) 19 | OVERLAY 20 | 1 1'Short Long' 21 | REC 5S 0H 22 | R WINDOW 23 | WINDOW(&SL &SP 15 41) 24 | WDWTITLE((*TEXT ' Select one ') - 25 | (*DSPATR RI)) 26 | SL 3S 0P 27 | SP 3S 0P 28 | 14 1'F12=Cancel' 29 | COLOR(BLU) -------------------------------------------------------------------------------- /tests/general/sms.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | ctl-opt nomain; 4 | 5 | /include sms_h.rpgle 6 | 7 | 8 | // Send request to Twilio API, log and return response as DS 9 | dcl-proc sendSmsVerbose export; 10 | dcl-pi *N likeds(smsResponse); 11 | req likeds(smsRequest); 12 | end-pi; 13 | 14 | dcl-ds resp likeds(smsResponse); 15 | dcl-s resp_rs sqltype(RESULT_SET_LOCATOR); 16 | 17 | exec SQL call send_sms(:req.phone_to, :req.phone_from, :req.msg, :req.account, :req.auth); 18 | exec SQL associate result set locator (:resp_rs) with procedure send_sms; 19 | exec SQL allocate c1 cursor for result set :resp_rs; 20 | exec SQL fetch next from c1 into :resp; 21 | exec SQL close c1; 22 | exec SQL insert into sms_log values(:resp); // log response 23 | 24 | return resp; 25 | end-proc; 26 | 27 | 28 | // Send request to Twilio API, log and return error code. 29 | // For simple requests where we don't care about the details immediately. 30 | // We just care whether it successfully sent the request 31 | dcl-proc sendSms export; 32 | dcl-pi *N varchar(8); 33 | phone_to varchar(16); 34 | phone_from varchar(16); 35 | msg varchar(1600); 36 | account varchar(64); 37 | auth varchar(64); 38 | end-pi; 39 | 40 | dcl-ds resp likeds(smsResponse); 41 | dcl-ds req likeds(smsRequest); 42 | 43 | req.phone_to = phone_to; 44 | req.phone_from = phone_from; 45 | req.msg = msg; 46 | req.account = account; 47 | req.auth = auth; 48 | 49 | resp = sendSmsVerbose(req); 50 | return resp.error_code; 51 | end-proc; -------------------------------------------------------------------------------- /tests/general/test.cmd: -------------------------------------------------------------------------------- 1 | /*-----------------------------------------------------------------*/ 2 | /* */ 3 | /* Sample command definition. */ 4 | /* */ 5 | /*-----------------------------------------------------------------*/ 6 | 7 | cmd prompt( 'Sample Command Definition' ) text( *cmdpmt ) + 8 | allow( *bpgm *ipgm *bmod *imod *brexx *irexx ) 9 | 10 | parm Obj QUALOBJ min( 1 ) prompt( 'Qualified object' ) 11 | parm YesNo1 *char 4 dft( *NO ) rstd( *yes ) values( *YES *NO ) + 12 | expr( *yes ) prompt( 'Yes or No value 1' ) 13 | parm YesNo2 *char 4 dft( *YES ) rstd( *yes ) values( *YES *NO ) + 14 | expr( *yes ) prompt( 'Yes or No value 2' ) 15 | parm PmtTest *name 10 dft( *NONE ) spcval( ( *NONE ' ' ) ) + 16 | expr( *yes ) pmtctl( YESNOYES) prompt( 'Prompt testing' ) 17 | 18 | QUALOBJ: qual *name 10 expr( *yes ) 19 | qual *name 10 dft( *LIBL ) spcval( *CURLIB *LIBL ) + 20 | prompt( 'Library' ) 21 | 22 | YESNOYES: pmtctl YesNo1 ( ( *eq *YES ) ) 23 | 24 | dep ctl( YesNo1 ) parm( ( YesNo2 *ne YesNo1 ) ) msgid(CPF9898) 25 | -------------------------------------------------------------------------------- /tests/issues/108.clp: -------------------------------------------------------------------------------- 1 | /* https://github.com/barrettotte/vscode-ibmi-languages/issues/108 */ 2 | 3 | READ_DSD: 4 | RCVF RCDFMT(EMLDSDRF) OPNID(DSD) 5 | MONMSG MSGID(CPF0000) EXEC(GOTO CMDLBL(EOF_DSD)) 6 | 7 | IF COND(&DSD_EDFILE *NE ' ') THEN(DO) 8 | 9 | CHGVAR VAR(&TOFILE) VALUE(&DSD_EDFILE *TCAT '.' *TCAT + 10 | &DSD_EDFILETYP) 11 | 12 | IF (&DSD_EDFILEPATH *EQ '*USER') THEN(DO) 13 | CHGVAR VAR(&FILEPATH) VALUE('/home/' *TCAT &USER) 14 | CHGVAR VAR(&FILEPATH2) VALUE('\\' *CAT &NETSHR + 15 | *TCAT '\home\' *TCAT &USER) 16 | ENDDO 17 | ELSE CMD(DO) 18 | CHGVAR VAR(&FILEPATH) VALUE(&DSD_EDFILEPATH) 19 | CHGVAR VAR(&SCANVAR) VALUE(&DSD_EDFILEPATH) 20 | SCNUPDVAR UPDVAR(&SCANVAR) PATTERN('/') RPLVALUE('\') + 21 | MULTSCAN(*YES) 22 | CHGVAR VAR(&FILEPATH2) VALUE('\\' *CAT &NETSHR + 23 | *TCAT &SCANVAR) 24 | ENDDO 25 | 26 | IF (&FILEPATH *GT ' ') THEN(DO) 27 | MD DIR(&FILEPATH) 28 | MONMSG MSGID(CPFA0A0) 29 | MONMSG MSGID(CPF0000) EXEC(DO) 30 | CLOF OPNID(EMLDSDPF) 31 | CALLSUBR SUBR(STDERR) 32 | ENDDO 33 | ENDDO 34 | 35 | CHGVAR VAR(&FILENAME) VALUE(&FILEPATH *TCAT '/' *TCAT + 36 | &TOFILE) 37 | CHGVAR VAR(&FILENAME2) VALUE(&FILEPATH2 *TCAT '\' + 38 | *TCAT &TOFILE) 39 | 40 | CHGVAR VAR(&LOCKEDFILE) VALUE('N') -------------------------------------------------------------------------------- /tests/issues/57.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/57 4 | 5 | // DEBUG(*RETVAL) 6 | ctl-opt debug(*RETVAL); 7 | 8 | 9 | // REQPREXP - https://www.ibm.com/support/pages/node/6342897 10 | ctl-opt reqprexp(*WARN); // *NO, *REQUIRE 11 | 12 | 13 | // EXPROPTS - https://www.ibm.com/support/pages/node/6342819 14 | ctl-opt expropts(*ALWBLANKNUM); // *USEDECEDIT 15 | 16 | dcl-s num packed(5:2); 17 | dcl-s str char(20); 18 | 19 | str = *blanks; 20 | num = %dec(str:63:5); // num = 0 21 | 22 | 23 | // %RANGE - https://www.ibm.com/support/pages/node/6342821 24 | if %date() in %range(min_register_date: max_register_date); 25 | processRegistration(); // the date is in range 26 | endif; 27 | 28 | 29 | // %LIST - https://www.ibm.com/support/pages/node/6342821 30 | dcl-s names varchar(20) dim(3); 31 | names = %list('Mary': 'Jack': 'Alice'); 32 | 33 | 34 | // IN - https://www.ibm.com/support/pages/node/6342821 35 | dcl-s sale_cities varchar(20) dim(10); 36 | dcl-s num_sale_cities int(10); 37 | 38 | if city in %subarr(sale_cities: 1: num_sale_cities); 39 | if cust_status in %list(STATUS_PREFERRED: STATUS_GOLD); 40 | subtract_discount(); 41 | endif; 42 | endif; 43 | 44 | 45 | // FOR-EACH - https://www.ibm.com/support/pages/node/6342821 46 | dcl-ds error likeds(error_t); 47 | dcl-ds errors likeds(error_t) dim(100); 48 | dcl-s num_errors int(10); 49 | dcl-s error_type int(10); 50 | dcl-s filename varchar(21); 51 | dcl-f logfile extdesc('LOGFILE_T') extname(filename); 52 | 53 | for-each filename in %list('CUR_ERRORS': 'ALL_ERRORS'); 54 | open logfile; 55 | for-each error in %subarr(errors: 1: num_errors); 56 | log_error_message(error); 57 | endfor; 58 | endfor; 59 | -------------------------------------------------------------------------------- /tests/issues/136.clle: -------------------------------------------------------------------------------- 1 | pgm 2 | 3 | dcl &@te@st@ *char 1 4 | dcl &#te#st# *char 1 5 | dcl &$te$st$ *char 1 6 | 7 | /* note: double click doesn't select full identifier */ 8 | /* but, single clicking highlights full identifier */ 9 | /* I guess that's the correct behavior? */ 10 | 11 | /* Additional variants: https://docs.google.com/spreadsheets/d/1J4yEGkfhtmACfdDVyD2XNJe0jjrIK77Um6-wsvW0etM/edit?usp=sharing */ 12 | 13 | /* CCSID 273 (Austria and Germany) */ 14 | dcl &@te@st@ *char 1 15 | dcl &§te§st§ *char 1 16 | dcl &$te$st$ *char 1 17 | 18 | /* CCSID 277 (Denmark and Norway) */ 19 | dcl &ØteØstØ *char 1 20 | dcl &ÆteÆstÆ *char 1 21 | dcl &ÅteÅstÅ *char 1 22 | 23 | /* CCSID 278 (Finland and Sweden) */ 24 | dcl &ÖteÖstÖ *char 1 25 | dcl &ÄteÄstÄ *char 1 26 | dcl &ÅteÅstÅ *char 1 27 | 28 | /* CCSID 280 (Italy) */ 29 | dcl &§te§st§ *char 1 30 | dcl &£te£st£ *char 1 31 | dcl &$te$st$ *char 1 32 | 33 | /* CCSID 284 (Spain and Latin America) */ 34 | dcl &@te@st@ *char 1 35 | dcl &ÑteÑstÑ *char 1 36 | dcl &$te$st$ *char 1 37 | 38 | /* CCSID 285 (Ireland and the United Kingdom) */ 39 | dcl &@te@st@ *char 1 40 | dcl &#te#st# *char 1 41 | dcl &£te£st£ *char 1 42 | 43 | /* CCSID 290 (Japan (katakana)) */ 44 | dcl &@te@st@ *char 1 45 | dcl &#te#st# *char 1 46 | dcl &¥te¥st¥ *char 1 47 | 48 | /* CCSID 297 (France) */ 49 | dcl &àteàstà *char 1 50 | dcl &£te£st£ *char 1 51 | dcl &$te$st$ *char 1 52 | 53 | /* CCSID 423 (Greece) */ 54 | dcl &§te§st§ *char 1 55 | dcl &£te£st£ *char 1 56 | dcl &$te$st$ *char 1 57 | 58 | /* CCSID 871 (Iceland) */ 59 | dcl &ÐteÐstÐ *char 1 60 | dcl &#te#st# *char 1 61 | dcl &$te$st$ *char 1 62 | 63 | /* CCSID 905 (Turkey - Latin-3) */ 64 | dcl &ŞteŞstŞ *char 1 65 | dcl &ÖteÖstÖ *char 1 66 | dcl &İteİstİ *char 1 67 | 68 | endpgm -------------------------------------------------------------------------------- /tests/general/ifsread.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // Return IFS file as string 3 | 4 | ctl-opt main(main); 5 | ctl-opt option(*srcstmt:*nodebugio:*nounref) dftactgrp(*no); 6 | 7 | dcl-pr main extpgm('IFSREAD'); 8 | *n char(127); 9 | *n char(4096); 10 | end-pr; 11 | 12 | dcl-pr fopen pointer extproc('_C_IFS_fopen'); 13 | fileName pointer value options(*string); 14 | fileMode pointer value options(*string); 15 | end-pr; 16 | 17 | dcl-pr fgets pointer extproc('_C_IFS_fgets'); 18 | line pointer value; 19 | size int(10) value; 20 | fstream pointer value; 21 | end-pr; 22 | 23 | dcl-pr fclose int(10) extproc('_C_IFS_fclose'); 24 | fstream pointer value; 25 | end-pr; 26 | 27 | 28 | dcl-proc main; 29 | dcl-pi *n; 30 | fpath char(127); 31 | fcontents char(4096); 32 | end-pi; 33 | 34 | dcl-s fp char(127) inz(*blanks); 35 | 36 | fp = %trim(fpath) + x'00'; 37 | 38 | monitor; 39 | fcontents = readFileContents(fp); 40 | on-error; 41 | dsply ('Fatal error occurred reading file.'); 42 | return; 43 | endmon; 44 | 45 | on-exit; 46 | *inlr = *on; 47 | return; 48 | end-proc; 49 | 50 | 51 | // read file contents into string 52 | dcl-proc readFileContents; 53 | dcl-pi *N varchar(4096); 54 | fpath char(128) value; 55 | end-pi; 56 | 57 | dcl-s fptr pointer; 58 | dcl-s contents varchar(4096); 59 | dcl-s lineBuffer char(128); 60 | dcl-s fmode char(5); 61 | 62 | fmode = 'r' + x'00'; 63 | fptr = fopen(%addr(fpath): %addr(fmode)); 64 | 65 | if (fptr = *null); 66 | dsply ('Could not open file'); 67 | return contents; 68 | endif; 69 | 70 | dow (fgets(%addr(lineBuffer): %size(lineBuffer): fptr) <> *null); 71 | lineBuffer = %xlate(x'00250D': ' ': lineBuffer); // LF,CR,NULL 72 | contents += %trimr(lineBuffer); 73 | clear lineBuffer; 74 | enddo; 75 | 76 | fclose(%addr(fpath)); 77 | return contents; 78 | end-proc; -------------------------------------------------------------------------------- /configurations/rpg.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"], 7 | 8 | ["IF", "ENDIF"], 9 | ["IF", "END"], 10 | ["IFEQ", "ENDIF"], 11 | ["IFEQ", "END"], 12 | ["IFGE", "ENDIF"], 13 | ["IFGE", "END"], 14 | ["IFGT", "ENDIF"], 15 | ["IFGT", "END"], 16 | ["IFLE", "ENDIF"], 17 | ["IFLE", "END"], 18 | ["IFLT", "ENDIF"], 19 | ["IFLT", "END"], 20 | ["IFNE", "ENDIF"], 21 | ["IFNE", "END"], 22 | 23 | ["DOW", "ENDDO"], 24 | ["DOW", "END"], 25 | ["DOWEQ", "ENDDO"], 26 | ["DOWEQ", "END"], 27 | ["DOWGE", "ENDDO"], 28 | ["DOWGE", "END"], 29 | ["DOWGT", "ENDDO"], 30 | ["DOWGT", "END"], 31 | ["DOWLE", "ENDDO"], 32 | ["DOWLE", "END"], 33 | ["DOWLT", "ENDDO"], 34 | ["DOWLT", "END"], 35 | ["DOWNE", "ENDDO"], 36 | ["DOWNE", "END"], 37 | 38 | ["DOU", "ENDDO"], 39 | ["DOU", "END"], 40 | ["DOUEQ", "ENDDO"], 41 | ["DOUQ", "END"], 42 | ["DOUGE", "ENDDO"], 43 | ["DOUGE", "END"], 44 | ["DOUGT", "ENDDO"], 45 | ["DOUGT", "END"], 46 | ["DOULE", "ENDDO"], 47 | ["DOULE", "END"], 48 | ["DOULT", "ENDDO"], 49 | ["DOULT", "END"], 50 | ["DOUNE", "ENDDO"], 51 | ["DOUNE", "END"], 52 | 53 | ["DO", "ENDDO"], 54 | ["DO", "END"], 55 | ["SELECT", "ENDSL"], 56 | ["SELECT", "END"], 57 | 58 | ["BEGSR", "ENDSR"] 59 | ], 60 | // symbols that are auto closed when typing 61 | "autoClosingPairs": [ 62 | //["{", "}"], 63 | ["[", "]"], 64 | ["(", ")"], 65 | ["\"", "\""], 66 | ["'", "'"] 67 | ], 68 | // symbols that that can be used to surround a selection 69 | "surroundingPairs": [ 70 | ["{", "}"], 71 | ["[", "]"], 72 | ["(", ")"], 73 | ["\"", "\""], 74 | ["'", "'"] 75 | ] 76 | } -------------------------------------------------------------------------------- /tests/issues/136.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | dcl-s @te@st@ char(16) inz(*blanks); 4 | dcl-s #te#st# char(16) inz(*blanks); 5 | dcl-s $te$st$ char(16) inz(*blanks); 6 | 7 | // note: double click doesn't select full identifier 8 | // but, single clicking highlights full identifier 9 | // I guess that's the correct behavior? 10 | 11 | // Additional variants: https://docs.google.com/spreadsheets/d/1J4yEGkfhtmACfdDVyD2XNJe0jjrIK77Um6-wsvW0etM/edit?usp=sharing 12 | 13 | // CCSID 273 (Austria and Germany) 14 | dcl-s @te@st@ char(16) inz(*blanks); 15 | dcl-s §te§st§ char(16) inz(*blanks); 16 | dcl-s $te$st$ char(16) inz(*blanks); 17 | 18 | // CCSID 277 (Denmark and Norway) 19 | dcl-s ØteØstØ char(16) inz(*blanks); 20 | dcl-s ÆteÆstÆ char(16) inz(*blanks); 21 | dcl-s ÅteÅstÅ char(16) inz(*blanks); 22 | 23 | // CCSID 278 (Finland and Sweden) 24 | dcl-s ÖteÖstÖ char(16) inz(*blanks); 25 | dcl-s ÄteÄstÄ char(16) inz(*blanks); 26 | dcl-s ÅteÅstÅ char(16) inz(*blanks); 27 | 28 | // CCSID 280 (Italy) 29 | dcl-s §te§st§ char(16) inz(*blanks); 30 | dcl-s £te£st£ char(16) inz(*blanks); 31 | dcl-s $te$st$ char(16) inz(*blanks); 32 | 33 | // CCSID 284 (Spain and Latin America) 34 | dcl-s @te@st@ char(16) inz(*blanks); 35 | dcl-s ÑteÑstÑ char(16) inz(*blanks); 36 | dcl-s $te$st$ char(16) inz(*blanks); 37 | 38 | // CCSID 285 (Ireland and the United Kingdom) 39 | dcl-s @te@st@ char(16) inz(*blanks); 40 | dcl-s #te#st# char(16) inz(*blanks); 41 | dcl-s £te£st£ char(16) inz(*blanks); 42 | 43 | // CCSID 290 (Japan (katakana)) 44 | dcl-s @te@st@ char(16) inz(*blanks); 45 | dcl-s #te#st# char(16) inz(*blanks); 46 | dcl-s ¥te¥st¥ char(16) inz(*blanks); 47 | 48 | // CCSID 297 (France) 49 | dcl-s àteàstà char(16) inz(*blanks); 50 | dcl-s £te£st£ char(16) inz(*blanks); 51 | dcl-s $te$st$ char(16) inz(*blanks); 52 | 53 | // CCSID 423 (Greece) 54 | dcl-s §te§st§ char(16) inz(*blanks); 55 | dcl-s £te£st£ char(16) inz(*blanks); 56 | dcl-s $te$st$ char(16) inz(*blanks); 57 | 58 | // CCSID 871 (Iceland) 59 | dcl-s ÐteÐstÐ char(16) inz(*blanks); 60 | dcl-s #te#st# char(16) inz(*blanks); 61 | dcl-s $te$st$ char(16) inz(*blanks); 62 | 63 | // CCSID 905 (Turkey - Latin-3) 64 | dcl-s ŞteŞstŞ char(16) inz(*blanks); 65 | dcl-s ÖteÖstÖ char(16) inz(*blanks); 66 | dcl-s İteİstİ char(16) inz(*blanks); 67 | -------------------------------------------------------------------------------- /dev/mi/mi.txt: -------------------------------------------------------------------------------- 1 | YIELD|XORSTR|XOR|XLATWTDS|XLATEWT|XLATEMB|XLATEB1|XLATEB|XLATE|XFRLOCK|XCTL|WAITTIME|VERIFY|UNLOCKSL|UNLOCK|UNLKMTX|UNLCKTSL|TSTRPLC|TSTINLTH|TSTBUM|TSTBTS|TRIML|TESTULA|TESTTOBJ|TESTSUBSET|TESTRPL|TESTPTR|TESTPDC|TESTINTR|TESTEXCP|TESTEAU|TESTAU|TANH|TAN|SYNCSTG|SUBSPPFO|SUBSPP|SUBN|SUBLC|STSPPO|STPLLEN|SSCA|SNSEXCPD|STRNCPYNULLPAD|STRNCPYNULL|STRNCMPNULL|STRLENNULL|SINH|SIN|SIGEXCP|SETSPPO|SETSPPFP|SETSPPD|SETSPP|SETSPFP|SETIP|SETINVF|SETIEXIT|SETHSSMK|SETDPAT|SETDPADR|SETDP|SETCA|SETBTS|SETALLEN|SETACST|SEARCH|SCANX|SCANWC|SCAN|SCALE|RTX|RTNEXCP|RSLVSP|RSLVDP|RMVINXEN|RINZSTAT|RETTSADR|RETTHID|RETTHCNT|RETINVF|RETEXCPD|RETCA|REM|REALCHSS|QUANTIZEBV|QUANTIZEBE|PROPB|POWER|POPPAR8|POPPAR4|POPCNTB|POPCNT8|POPCNT4|PCOPTR2|PCOPTR|OVRPGATR|ORSTR|OR|OPM_PARM_CNT|OPM_PARM_ADDR|NPM_PARMLIST_ADDR|NOT|NOOPS|NOOP|NEG|MPYSUB|MPYADD|MULT|MODS2|MODS1|MODS|MODINVAU|MODINX|MODEXCPD|MODASA|MEMUSEHINT|MEMMOVE|MEMCPY|MEMCMP|MATUPID|MATUP|MATTODAT|MATSOBJ|MATS|MATSELLK|MATRMD|MATQMSGQ|MATQAT|MATPGMNM|MATPG|MVLICOPT|MATPRMTX|MATPRMSG|MATPRLK|MATPRECL|MATPRATR|MATPRAGP|MATPTRL|MATPTRIF|MATPTR|MATOBJLCK|MATMTX|MATMIF|MATMDATA|MATMATR1|MATMATR|MATJSAT|MATJPAT|MATJOBJ|MATJOAT|MATINVS|MATINVE|MATINVAT|MATINV|MATINAT|MATINXAT|MATEXCPD|MATDMPS|MATDRECL|MATCTX|MATBPGM|MATAUU|MATAUOBJ|MATAL|MATAU|MATAOL|MATHSAT|MATAGPAT|MATACTEX|MATACTAT|MATAGAT|LN|LOCKTSL|LOCKSL|LOCKMTX|LOCK|INVP|INSINXEN|INITEHCA|INCTS|INCT|INCD|GENUUID|FREHSSMK|FREHSS|FNDRINVN|FNDINXEN|STRCHRNULL|MEMCHR|FINDBYTE|EXTRMAG|EXTREXP|ECSCAN|EEXP|EXCHBY|ENSOBJ|ENQ|END|EDITPD|LBEDIT|EDIT|DIVREM|DIV|DESS|DESMTX|DESINX|DESHS|DEQWAIT|DEQ|DECTS|DECT|DECD|DCPDATA|DEACTPG|CVTTS|CVTT|CVTSC|CVTNC|CVTMC|CVTHC|CVTFPDF|CVTEFN|CVTDFFP|CVTD|CVTCS|CVTCN|CVTCM|CVTCH|CVTCB|CVTBC|CTSD|CTD|CRTS|CRTMTX|CRTINX|CRTHS|CNTLZ8|CNTLZ4|COT|COSH|COS|LBCPYNVR|LBCPYNV|CPYNV|STRCPYNULL|CPYHEXZZ|CPYHEXZN|CPYHEXNZ|CPYHEXNN|CPYECLAP|CPYBWP|CPYBRAP|CPYBRA|CPYBREP|CPYBO|CPYBOLAP|CPYBOLA|CPYBLAP|CPYBLA|CPYBBTL|CPYBBTA|CPYBYTES|CPYBTRLS|CPYBTRAS|CPYBTLLS|CPYBTL|CPYBTA|CPRDATA|CAT|CMPTOPAD|CMPSWP|CMPSW|CMPSPAD|CMPPTRT|CMPPTRE|CMPPTRA|CMPPSPAD|CMPPNV|STRCMPNULL|CMPBRAP|CMPBRA|CMPBLAP|CMPBLA|CMF2|CMF1|CDD|CAI|COMSTR|CLRLKVAL|CLRINVF|CLRIEXIT|CLRBTS|CIPHER|CHKLKVAL|CALLPGMV|CALLI|CALLX|B|BITPERM|ATMCOR|ATMCAND|ATMCADD|ATANH|ATAN|ASIN|ACOS|ANDSTR|ANDCSTR|AND|ALCHSS|ADDSPP|ADDN|ADDLC|ACTPG|ACTBPGM -------------------------------------------------------------------------------- /tests/general/test.pnlgrp: -------------------------------------------------------------------------------- 1 | .*------------------------------------------------------------------------------------------------*. 2 | .* *. 3 | .* Start Ungit server. *. 4 | .* *. 5 | .* Create Instructions: *. 6 | .* *. 7 | .*> CRTFRMSTMF OBJ(&FCN2/&FNR) CMD(CRTPNLGRP) SRCSTMF('&FP') <*. 8 | .*> CHGOBJD OBJ(&FCN2/&FNR) OBJTYPE(*PNLGRP) TEXT('Start Ungit server') <*. 9 | .* *. 10 | .*------------------------------------------------------------------------------------------------*. 11 | 12 | .im member1 13 | 14 | :pnlgrp. 15 | 16 | .* Help for command STRUNGIT: 17 | 18 | :help name='STRUNGIT'. 19 | STRUNGIT - Help 20 | :P. 21 | This command starts an Ungit server job. 22 | :p. 23 | The Ungit server job provides a server for the Ungit user interface. 24 | The Ungit user interface is a clean and intuitive UI that makes it easy to use and understand git. 25 | :p. 26 | :lines. 27 | For more information see the following link: 28 | https://github.com/FredrikNoren/ungit 29 | :elines. 30 | :ehelp. 31 | 32 | .*------------------------------------------------------------------------------------------------*. 33 | .* Help for parameter USRPRF: 34 | 35 | :help name='STRUNGIT/USRPRF'. 36 | User profile (USRPRF) - Help 37 | :xh3.User profile (USRPRF) 38 | :p.Specifies the user profile for which to start the Ungit server. 39 | .* 40 | :parml. 41 | :pt.:pk def.*CURRENT:epk. 42 | :pd. 43 | Use the current user profile. 44 | .* 45 | :pt.:pv.name:epv. 46 | :pd. 47 | Specify the user profile to use. 48 | .* 49 | :eparml. 50 | :ehelp. 51 | 52 | .*------------------------------------------------------------------------------------------------*. 53 | .* Help for parameter OPTIONS: 54 | 55 | :help name='STRUNGIT/OPTIONS'. 56 | Ungit options (OPTIONS) - Help 57 | :xh3.Ungit options (OPTIONS) 58 | :p.Specifies any extra options used when starting the Ungit server. 59 | :nt.Do not use the options --port and --ungitBindIp - these are used by the STRUNGIT command.:ent. 60 | .* 61 | :parml. 62 | :pt.:pk def.*NONE:epk. 63 | :pd. 64 | No extra options will be used. 65 | .* 66 | :pt.:pv.Text:epv. 67 | :pd. 68 | Specify the extra options to use. 69 | .* 70 | :eparml. 71 | :ehelp. 72 | 73 | :epnlgrp. 74 | -------------------------------------------------------------------------------- /syntaxes/bnd.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "BND", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#strings" 16 | }, 17 | { 18 | "include": "#support" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.bnd", 26 | "begin": "(\\/\\*)", 27 | "end": "(\\*\\/)" 28 | }, 29 | { 30 | "name": "comment.line.bnd", 31 | "begin": "\\-\\-", 32 | "end": "\n" 33 | } 34 | ] 35 | }, 36 | "constants": { 37 | "patterns": [ 38 | { 39 | "name": "constant.numeric.bnd", 40 | "match": "(\\b[0-9]+)|([0-9]*[.][0-9]*)" 41 | }, 42 | { 43 | "name": "constant.language.bnd", 44 | "match": "[*][a-zA-Z][a-zA-Z0-9]*" 45 | } 46 | ] 47 | }, 48 | "keywords": { 49 | "patterns": [ 50 | { 51 | "name": "keyword.other.bnd", 52 | "match": "(?i)(STRPGMEXP|ENDPGMEXP|EXPORT)" 53 | }, 54 | { 55 | "name": "keyword.other.bnd", 56 | "match": "<" 57 | } 58 | ] 59 | }, 60 | "strings": { 61 | "patterns": [ 62 | { 63 | "name": "string.other.bnd.hex", 64 | "begin": "(?i)x'", 65 | "end": "'" 66 | }, 67 | { 68 | "name": "string.quoted.single.bnd", 69 | "begin": "('|\")", 70 | "end": "'|\"", 71 | "patterns": [ 72 | { 73 | "name": "constant.character.escape.bnd", 74 | "match": "\\\\." 75 | } 76 | ] 77 | } 78 | ] 79 | }, 80 | "support": { 81 | "patterns": [ 82 | { 83 | "name": "support.function.bnd", 84 | "match": "(?i)[A-Za-z]+(?=\\()" 85 | } 86 | ] 87 | } 88 | }, 89 | "scopeName": "source.bnd" 90 | } -------------------------------------------------------------------------------- /configurations/rpgle.language-configuration.json: -------------------------------------------------------------------------------- 1 | { 2 | // symbols used as brackets 3 | "brackets": [ 4 | ["{", "}"], 5 | ["[", "]"], 6 | ["(", ")"], 7 | 8 | ["IF", "ENDIF"], 9 | ["IF", "END"], 10 | ["IFEQ", "ENDIF"], 11 | ["IFEQ", "END"], 12 | ["IFGE", "ENDIF"], 13 | ["IFGE", "END"], 14 | ["IFGT", "ENDIF"], 15 | ["IFGT", "END"], 16 | ["IFLE", "ENDIF"], 17 | ["IFLE", "END"], 18 | ["IFLT", "ENDIF"], 19 | ["IFLT", "END"], 20 | ["IFNE", "ENDIF"], 21 | ["IFNE", "END"], 22 | 23 | ["DOW", "ENDDO"], 24 | ["DOW", "END"], 25 | ["DOWEQ", "ENDDO"], 26 | ["DOWEQ", "END"], 27 | ["DOWGE", "ENDDO"], 28 | ["DOWGE", "END"], 29 | ["DOWGT", "ENDDO"], 30 | ["DOWGT", "END"], 31 | ["DOWLE", "ENDDO"], 32 | ["DOWLE", "END"], 33 | ["DOWLT", "ENDDO"], 34 | ["DOWLT", "END"], 35 | ["DOWNE", "ENDDO"], 36 | ["DOWNE", "END"], 37 | 38 | ["DOU", "ENDDO"], 39 | ["DOU", "END"], 40 | ["DOUEQ", "ENDDO"], 41 | ["DOUQ", "END"], 42 | ["DOUGE", "ENDDO"], 43 | ["DOUGE", "END"], 44 | ["DOUGT", "ENDDO"], 45 | ["DOUGT", "END"], 46 | ["DOULE", "ENDDO"], 47 | ["DOULE", "END"], 48 | ["DOULT", "ENDDO"], 49 | ["DOULT", "END"], 50 | ["DOUNE", "ENDDO"], 51 | ["DOUNE", "END"], 52 | 53 | ["DO", "ENDDO"], 54 | ["DO", "END"], 55 | 56 | // not ideal, but commented out because SQLRPGPLE selects are probably more common 57 | // than select cases...I think to properly fix this, it would have to be solved via language server 58 | //["SELECT", "ENDSL"], 59 | //["SELECT", "END"], 60 | 61 | ["FOR-EACH", "ENDFOR"], 62 | ["FOR-EACH", "END"], 63 | ["FOR", "ENDFOR"], 64 | ["FOR", "END"], 65 | 66 | ["BEGSR", "ENDSR"], 67 | ["MONITOR", "ENDMON"], 68 | ["DCL-DS", "END-DS"], 69 | ["DCL-PROC", "END-PROC"], 70 | ["DCL-PR", "END-PR"], 71 | ["DCL-PI", "END-PI"], 72 | 73 | ["EXEC SQL", ";"], 74 | ], 75 | // symbols that are auto closed when typing 76 | "autoClosingPairs": [ 77 | //["{", "}"], 78 | ["[", "]"], 79 | ["(", ")"], 80 | ["\"", "\""], 81 | ["'", "'"] 82 | ], 83 | // symbols that that can be used to surround a selection 84 | "surroundingPairs": [ 85 | ["{", "}"], 86 | ["[", "]"], 87 | ["(", ")"], 88 | ["\"", "\""], 89 | ["'", "'"] 90 | ], 91 | "comments": { 92 | "lineComment": "//" 93 | }, 94 | "wordPattern": "(-?\\d*\\.\\d\\w*)|([^\\`\\~\\!\\%\\^\\&\\*\\(\\)\\-\\=\\+\\[\\{\\]\\}\\\\\\|\\;\\:\\'\\\"\\,\\.\\<\\>\\/\\?\\s]+)" 95 | } -------------------------------------------------------------------------------- /tests/issues/152.dspf: -------------------------------------------------------------------------------- 1 | A DSPSIZ(24 80 *DSP3) 2 | A CHGINPDFT(HI UL) 3 | A CA03(03 'Exit') 4 | A CA12(12 'Cancel') 5 | A R TESTR 6 | A*%%TS SD 20250329 154927 LENNONS REL-V7R5M0 5770-WDS 7 | A* 8 | A A#SNG1 1Y 0H 9 | A A#SNG2 1Y 0H 10 | A A#SNG3 1Y 0H 11 | A A#SNG1T 5A P 12 | A A#SNG2T 5A P 13 | A A#SNG3T 5A P 14 | A A#MLT1 1Y 0H 15 | A A#MLT3 1Y 0H 16 | A A#MLT2 1Y 0H 17 | A A#MLT1T 5A P 18 | A A#MLT2T 5A P 19 | A A#MLT3T 5A P 20 | A 11 50'Status' 21 | A 11 64'Ship' 22 | A 12 3'Product:' 23 | A PRODUCT 30A B 12 12DSPATR(UL) 24 | A* 25 | A 02 P1DESC 5A O 12 51 26 | A N02 P1ANR 2Y 0B 12 51SNGCHCFLD(*RSTCSR *AUTOSLT *SLTIND - 27 | A (*NUMROW 3)) 28 | A N01 CHCAVAIL((*COLOR TRQ) (*DSPATR HI)) 29 | A 01 CHCUNAVAIL((*COLOR WHT) (*DSPATR HI- 30 | A )) 31 | A CHOICE(1 &A#SNG1T) 32 | A CHCCTL(1 &A#SNG1) 33 | A CHOICE(2 &A#SNG2T) 34 | A CHCCTL(2 &A#SNG2) 35 | A CHOICE(3 &A#SNG3T) 36 | A CHCCTL(3 &A#SNG3) 37 | A* 38 | A 02 P2DESC1 5A O 12 65 39 | A 02 P2DESC2 5A O 13 65 40 | A 02 P2DESC3 5A O 14 65 41 | A N02 P2INT 2Y 0B 12 65MLTCHCFLD(*RSTCSR *SLTIND (*NUMROW - 42 | A 3)) 43 | A N01 CHCAVAIL((*COLOR PNK) (*DSPATR HI)) 44 | A 01 CHCUNAVAIL((*COLOR WHT) (*DSPATR HI- 45 | A )) 46 | A CHOICE(1 &A#MLT1T) 47 | A CHCCTL(1 &A#MLT1) 48 | A CHOICE(2 &A#MLT2T) 49 | A CHCCTL(2 &A#MLT2) 50 | A CHOICE(3 &A#MLT3T) 51 | A CHCCTL(3 &A#MLT3) 52 | A 02 MSG 70A O 17 10 53 | -------------------------------------------------------------------------------- /tests/general/test1.rpg: -------------------------------------------------------------------------------- 1 | H/TITLE Testing syntax highlighting 2 | * 3 | H* Control spec (H prompt) 4 | H 1 Y&J D 1 F QWERTY 5 | * 6 | F* Externally described file (FX prompt) 7 | FSOMEFILEIFEAE L K DISK K A UC comment 8 | * 9 | F* Program described file (F prompt) 10 | FSOMEFIL2OPEDF ATOV LPRINTER K A U6 comment 11 | * 12 | E* Extension spec (E prompt) 13 | E FFILE TFILE ATBL 1239999128L6AALTNAM64 P8DTHIS IS A COMMENT 14 | * 15 | L* Line Counter spec (L prompt) 16 | LSOMEFILE101FL300OL comment 17 | * 18 | I* Input spec record identification (I prompt) 19 | ISOMEFILE3ANOL41 NZX2 CA3 ND4 comment 20 | I* 21 | I* Input spec record identification external (IX prompt) 22 | IMYRECORD H4 comment 23 | I* Input spec field description (J prompt) 24 | I P123499997MYFLD L4M2RTH4U7H6 comment 25 | I* Input spec field description external (JX prompt) 26 | I EXTFILENAM MYFLD L4M5 U3RTH7 comment 27 | I* Data structure input specification (DS prompt) 28 | IMYDS EUDSEXTFILENAM 12345555 comment 29 | I* Data structure subfield input spec (SS prompt) 30 | I EXTFLDNAME P123488885MYFLD comment 31 | I* Data structure subfield init spec (SV prompt) 32 | I I SOMETHING P123456785MYFLD comment 33 | * 34 | C* Calc spec (C prompt) 35 | CLRNLR MRNL1VARA ADD VARB RES 30 1HOV02H2COMMENT! 36 | * 37 | C* Test embedded SQL 38 | * 39 | * -- ENTRY PARMS 40 | C/COPY SRCLIB/QCPYSRC,ENC320C comment 41 | C* 42 | * 43 | C/Exec SQL 44 | C+ select count(*) 45 | C+ into :VAR123 46 | C+ from MYTABLE 47 | C+ where COL1 = :VAR4 and COL2 = 0 48 | C+ and SUBSTR(DATA,1,4)='WASD' 49 | C/End-Exec 50 | * 51 | O* Output spec (O prompt) 52 | O NKA 01 L2FIELDXJB+NNNPWASD comment 53 | O* Output spec disk (OD prompt) 54 | OMYFILE TADD NKA L4NRTWASD comment 55 | O* Output spec field description (P prompt) 56 | O NKA L4NU2MYFLDMXBNNNNLMYCONST comment 57 | O N01 L2NKNSEATS# 200B comment 58 | * 59 | /EJECT 60 | /COPY 61 | ** TABER# / TABERD 62 | 1Text Text Text Text. 63 | 2Text Text Text Text Text Text Text Text Text Text. 64 | 3Text Text Text Text Text Text Text Text. 65 | 4 66 | 5 67 | 6 68 | 7 69 | 8 -------------------------------------------------------------------------------- /tests/issues/61.rpg: -------------------------------------------------------------------------------- 1 | H* https://github.com/barrettotte/vscode-ibmi-languages/issues/61 2 | H* 3 | H* https://raw.githubusercontent.com/worksofliam/flight400/master/qrpgsrc/frs409.rpg 4 | H* 5 | FFRS409DFCF E WORKSTN KINFDS WSDS 6 | I* 7 | I X'31' C @F01 8 | I X'33' C @F03 9 | I X'3C' C @F12 10 | I X'F1' C @ENTER 11 | I X'F3' C @HELP 12 | I X'F6' C @PRINT 13 | I* 14 | I '0' C @FALSE 15 | I '1' C @TRUE 16 | I* 17 | IWSDS DS 18 | I 369 369 KEY 19 | C* 20 | C *ENTRY PLIST 21 | C PARM ORDER# 90 * RETURN START TIME 22 | C PARM ENDYN 1 * RETURN START TIME 23 | C* 24 | C EXSR INZSR * RESET EXIT FLAG 25 | C* 26 | C @EXIT DOUEQ@TRUE * DO UNTIL F3/F12 27 | C* 28 | C WRITEFRSWIN * WRITE MSGCTL 29 | C EXFMTFKEYS * WRITE SFL CMDL 30 | C* 31 | C KEY CASEQ@F03 @F03SR F03 EXIT 32 | C KEY CASEQ@F12 @F12SR F12 CANCEL 33 | C CAS @ENTKY Enter 34 | C ENDCS 35 | C* 36 | C NEXT TAG 37 | C ENDDO 38 | C* 39 | C MOVE *ON *INLR 40 | C* 41 | C* 42 | C* 43 | C INZSR BEGSR * INIT SUBROUTN 44 | C MOVE ORDER# ORDER * RETURN START TIME 45 | C MOVE 'N' ENDYN * RETURN START TIME 46 | C MOVE @FALSE @EXIT 1 * PGM EXIT = OFF 47 | C ENDSR 48 | C* 49 | C* 50 | C @ENTKY BEGSR 51 | C MOVE @TRUE @EXIT * SET EXIT FLAG ON 52 | C ENDSR 53 | C* 54 | C* 55 | C @F03SR BEGSR * F3 SUBROUTINE 56 | C MOVE 'Y' ENDYN * RETURN START TIME 57 | C MOVE @TRUE @EXIT * SET EXIT FLAG ON 58 | C ENDSR 59 | C* 60 | C* 61 | C @F12SR BEGSR 62 | C MOVE 'Y' ENDYN * RETURN START TIME 63 | C MOVE @TRUE @EXIT 64 | C ENDSR 65 | -------------------------------------------------------------------------------- /syntaxes/dds.pf.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "DDS.PF", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#gutter" 16 | }, 17 | { 18 | "include": "#strings" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.dds.pf", 26 | "match": "^.{5}(.)(\\*).*" 27 | } 28 | ] 29 | }, 30 | "gutter": { 31 | "patterns": [ 32 | { 33 | "name": "comment.gutter", 34 | "match": "^.{5}" 35 | } 36 | ] 37 | }, 38 | "constants": { 39 | "patterns": [ 40 | { 41 | "name": "constant.language.dds.pf", 42 | "match": "(\\*)[a-zA-Z][a-zA-Z0-9]*" 43 | }, 44 | { 45 | "name": "constant.language.dds.pf.nametype", 46 | "match": "(?i)(?<=^.{5}(A|\\s).{10})(R|K)" 47 | }, 48 | { 49 | "name": "constant.language.dds.pf.ref", 50 | "match": "(?i)(?<=^.{5}(A|\\s).{22})R" 51 | }, 52 | { 53 | "name": "constant.language.dds.pf.len", 54 | "match": "(?i)(?<=^.{5}(A|\\s).{23})[0-9|\\s]{5}" 55 | }, 56 | { 57 | "name": "constant.language.dds.pf.datatype", 58 | "match": "(?i)(?<=^.{5}(A|\\s).{28})(P|S|B|F|A|L|T|Z|H|J|E|O|G|5)" 59 | }, 60 | { 61 | "name": "constant.language.dds.pf.decpos", 62 | "match": "(?i)(?<=^.{5}(A|\\s).{29})([0-9]|\\s){2}" 63 | }, 64 | { 65 | "name": "constant.language.dds.pf.use", 66 | "match": "(?i)(?<=^.{5}(A|\\s).{31})(B)" 67 | }, 68 | { 69 | "name": "constant.numeric.dds.pf", 70 | "match": "(\\b[0-9]+)|([0-9]*[.][0-9]*)" 71 | } 72 | ] 73 | }, 74 | "keywords": { 75 | "patterns": [ 76 | { 77 | "name": "keyword.other.dds.pf.spec", 78 | "match": "(?i)(?<=^.{5})(A)" 79 | }, 80 | { 81 | "name": "keyword.other.dds.pf", 82 | "match": "\\+" 83 | }, 84 | { 85 | "name": "keyword.other.dds.pf.funcs", 86 | "match": "(?i)(?<=(.{44}))(?<=((?<=^.{5}[A|\\s]).{38}))(ZONE|VARLEN|VALUES|UNSIGNED|UNIQUE|TIMSEP|TIMFMT|TEXT|REFSHIFT|REFFLD|REF|RANGE|NOALTSEQ|LIFO|FORMAT|FLTPCN|FIFO|FCFO|EDTCDE|EDTWRD|DIGIT|DFT|DESCEND|DATSEP|DATFMT|COMP|COLHDG|CMP|CHKMSGID|CHECK|CCSID|ALWNULL|ALTSEQ|ALIAS|ABSVAL)\\b" 87 | } 88 | ] 89 | }, 90 | "identifiers": { 91 | "patterns": [ 92 | { 93 | "name": "identifier.other.dds.lf.identifiers", 94 | "match": "[a-zA-Z_#$][a-zA-Z0-9_.#$]*" 95 | } 96 | ] 97 | }, 98 | "strings": { 99 | "name": "string.quoted.single.dds.pf", 100 | "begin": "'", 101 | "end": "'", 102 | "patterns": [ 103 | { 104 | "name": "keyword.other.dds.pf.spec", 105 | "match": "(?i)(?<=^.{5})(A)" 106 | } 107 | ] 108 | } 109 | }, 110 | "scopeName": "source.dds.pf" 111 | } -------------------------------------------------------------------------------- /tests/general/test-free.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | ctl-opt actgrp(*new); 4 | 5 | dcl-s cusNum packed(7:0); 6 | dcl-s lstNam char(50); 7 | dcl-s cusCity char(30); 8 | dcl-s message varchar(100); 9 | 10 | 11 | // Main logic 12 | cusNum = 593029; 13 | 14 | // Execute SQL SELECT statement 15 | EXEC SQL 16 | SELECT LSTNAM, CITY 17 | INTO :lstNam, :cusCity 18 | FROM QIWS.QCUSTCDT 19 | WHERE CUSNUM = :cusNum; 20 | 21 | // Check SQLSTATE for errors 22 | if SQLSTATE = '00000'; 23 | 24 | // Success - display customer information 25 | snd-msg ('Customer: ' + %trim(lstNam)); 26 | snd-msg ('City: ' + %trim(cusCity)); 27 | 28 | elseif SQLSTATE = '02000'; 29 | 30 | // No data found 31 | message = 'Customer ' + %char(cusNum) + ' not found'; 32 | snd-msg message; 33 | 34 | else; 35 | 36 | // Other SQL error 37 | message = 'SQL Error - SQLSTATE: ' + SQLSTATE + 38 | ' SQLCODE: ' + %char(SQLCODE); 39 | snd-msg message; 40 | endif; 41 | 42 | 43 | snd-msg 'SQL Communication Area (SQLCA). ' + 44 | 'SQLCODE: ' + %char(SQLCODE) + 45 | ', SQLCOD: ' + %char(SQLCOD) + 46 | ', SQLERRML: ' + %char(SQLERRML) + 47 | ', SQLERL: ' + %char(SQLERL) + 48 | ', SQLERRMC: ' + %trimr(SQLERRMC) + 49 | ', SQLERM: ' + %trimr(SQLERM) + 50 | ', SQLERRP: ' + SQLERRP + 51 | ', SQLERP: ' + SQLERP + 52 | ', SQLERR: ' + SQLERR + 53 | ', SQLER1: ' + %char(SQLER1) + 54 | ', SQLER2: ' + %char(SQLER2) + 55 | ', SQLER3: ' + %char(SQLER3) + 56 | ', SQLER4: ' + %char(SQLER4) + 57 | ', SQLER5: ' + %char(SQLER5) + 58 | ', SQLER6: ' + %char(SQLER6) + 59 | ', SQLERRD(1): ' + %char(SQLERRD(1)) + 60 | ', SQLERRD(2): ' + %char(SQLERRD(2)) + 61 | ', SQLERRD(3): ' + %char(SQLERRD(3)) + 62 | ', SQLERRD(4): ' + %char(SQLERRD(4)) + 63 | ', SQLERRD(5): ' + %char(SQLERRD(5)) + 64 | ', SQLERRD(6): ' + %char(SQLERRD(6)) + 65 | ', SQLWRN: ' + SQLWRN + 66 | ', SQLWN0: ' + SQLWN0 + 67 | ', SQLWN1: ' + SQLWN1 + 68 | ', SQLWN2: ' + SQLWN2 + 69 | ', SQLWN3: ' + SQLWN3 + 70 | ', SQLWN4: ' + SQLWN4 + 71 | ', SQLWN5: ' + SQLWN5 + 72 | ', SQLWN6: ' + SQLWN6 + 73 | ', SQLWN7: ' + SQLWN7 + 74 | ', SQLWN8: ' + SQLWN8 + 75 | ', SQLWN9: ' + SQLWN9 + 76 | ', SQLWNA: ' + SQLWNA + 77 | ', SQLWARN(1): ' + SQLWARN(1) + 78 | ', SQLWARN(2): ' + SQLWARN(2) + 79 | ', SQLWARN(3): ' + SQLWARN(3) + 80 | ', SQLWARN(4): ' + SQLWARN(4) + 81 | ', SQLWARN(5): ' + SQLWARN(5) + 82 | ', SQLWARN(6): ' + SQLWARN(6) + 83 | ', SQLWARN(7): ' + SQLWARN(7) + 84 | ', SQLWARN(8): ' + SQLWARN(8) + 85 | ', SQLWARN(9): ' + SQLWARN(9) + 86 | ', SQLWARN(10): ' + SQLWARN(10) + 87 | ', SQLWARN(11): ' + SQLWARN(11) + 88 | ', SQLSTATE: ' + SQLSTATE + 89 | ', SQLSTT: ' + SQLSTT ; 90 | 91 | 92 | *inlr = *on; 93 | return; -------------------------------------------------------------------------------- /tests/general/test2.rpg: -------------------------------------------------------------------------------- 1 | F*************************************************************** 2 | F* THIS PROGRAM READS THE CONTENTS OF AN INVOICE HEADER FILE 3 | F* AND PRINTS THE INVOICES PROCESSED FOR THE DATE SET IN THE 4 | F* LOCAL DATA AREA. THERE ARE LEVEL BREAKS AND TOTALS FOR 5 | F* EACH STORE. 6 | F*************************************************************** 7 | F* 8 | F* Stolen from https://en.wikipedia.org/wiki/IBM_RPG_II 9 | F* 10 | FINVHDR IP F 62 DISK 11 | FPRINTER O F 132 OF PRINTER 12 | IINVHDR NS 01 1NC 13 | I 1 3 STORE L1 14 | I 4 13 INVNO 15 | I 14 20 CUSTNO 16 | I 21 45 STNAM 17 | I 46 53 INVDAT 18 | I 54 622TOTINV 19 | I UDS 20 | I 1 8 RPTDAT 21 | C 01 INVDAT COMP RPTDAT 11 22 | C 01 11 ADD TOTINV L1TOT 92 23 | C 01 11 ADD TOTINV LRTOT 92 24 | OPRINTER H 101 1P 25 | O OR OF 26 | O PAGE Z 106 27 | O 102 'PAGE' 28 | O 59 'VERY BIG' 29 | O 72 'STORES, INC.' 30 | O UDATE Y 17 31 | O 8 'RUN DATE' 32 | O H 1 1P 33 | O OR OF 34 | O 73 'DAILY SALES BY STORE' 35 | O H 2 1P 36 | O OR OF 37 | O RPTDAT 83 38 | O 63 'FOR DATE:' 39 | O H 1 1P 40 | O OR OF 41 | O 6 'STORE' 42 | O 18 'INVOICE' 43 | O 28 'CUSTOMER' 44 | O 58 'CUSTOMER' 45 | O 78 'INVOICE' 46 | O H 2 1P 47 | O OR OF 48 | O 6 'NUMBER' 49 | O 18 'NUMBER' 50 | O 28 'NUMBER' 51 | O 58 'NAME' 52 | O 78 'TOTAL' 53 | O D 0 L1 54 | O STORE 6 55 | O D 1 01 11 56 | O INVNO 18 57 | O CUSTNO 28 58 | O STNAM 58 59 | O TOTINV1B 78 60 | O T 1 L1 61 | O 45 'STORE TOTAL...' 62 | O L1TOT 1B 78 63 | O T 1 LR 64 | O 45 'GRAND TOTAL...' 65 | O LRTOT 1 78 -------------------------------------------------------------------------------- /syntaxes/dds.lf.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "DDS.LF", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#gutter" 16 | }, 17 | { 18 | "include": "#strings" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.dds.lf", 26 | "match": "^.{5}(.)(\\*).*" 27 | } 28 | ] 29 | }, 30 | "gutter": { 31 | "patterns": [ 32 | { 33 | "name": "comment.gutter", 34 | "match": "^.{5}" 35 | } 36 | ] 37 | }, 38 | "constants": { 39 | "patterns": [ 40 | { 41 | "name": "constant.language.dds.lf", 42 | "match": "(\\*)[a-zA-Z][a-zA-Z0-9]*" 43 | }, 44 | { 45 | "name": "constant.language.dds.lf.nametype", 46 | "match": "(?i)(?<=^.{5}(A|\\s).{10})(R|K|J|S|O)" 47 | }, 48 | { 49 | "name": "constant.language.dds.lf.ref", 50 | "match": "(?i)(?<=^.{5}(A|\\s).{22})R" 51 | }, 52 | { 53 | "name": "constant.language.dds.lf.len", 54 | "match": "(?i)(?<=^.{5}(A|\\s).{23})[0-9|\\s]{5}" 55 | }, 56 | { 57 | "name": "constant.language.dds.lf.datatype", 58 | "match": "(?i)(?<=^.{5}(A|\\s).{28})(P|S|B|F|A|L|T|Z|H|J|E|O|G|5)" 59 | }, 60 | { 61 | "name": "constant.language.dds.lf.decpos", 62 | "match": "(?i)(?<=^.{5}(A|\\s).{29})[0-9|\\s]{2}" 63 | }, 64 | { 65 | "name": "constant.language.dds.lf.use", 66 | "match": "(?i)(?<=^.{5}(A|\\s).{31})(B|I|N)" 67 | }, 68 | { 69 | "name": "constant.numeric.dds.lf", 70 | "match": "(\\b[0-9]+)|([0-9]*[.][0-9]*)" 71 | } 72 | ] 73 | }, 74 | "keywords": { 75 | "patterns": [ 76 | { 77 | "name": "keyword.other.dds.lf.spec", 78 | "match": "(?i)(?<=^.{5})[A]" 79 | }, 80 | { 81 | "name": "keyword.other.dds.lf", 82 | "match": "\\+" 83 | }, 84 | { 85 | "name": "keyword.other.dds.lf.funcs", 86 | "match": "(?i)(?<=(.{44}))(?<=((?<=^[\\s]{5}[A|\\s]).{38}))((ZONE|VARLEN|VALUES|UNSIGNED|UNIQUE|TIMSEP|TIMFMT|TEXT|SST|RENAME|REFSHIFT|REFACCPTH|RANGE|PFILE|NOALTSEQ|LIFO|JREF|JOIN|JFLD|JFILE|JDUPSEQ|JDFTVAL|FORMAT|FLTPCN|FIFO|FCFO|EDTCDE|EDTWRD|DYNSLT|DIGIT|DESCEND|DATSEP|DATFMT|CONCAT|COMP|COLHDG|CMP|CHKMSGID|CHECK|CCSID|ALTSEQ|ALL|ALIAS|ABSVAL)+)\\b" 87 | }, 88 | { 89 | "name": "dds.lf.comp", 90 | "begin": "(?i)(?<=(.{44}))((?<=((COMP)\\())|(?<=((CMP)\\()))", 91 | "end": "(?=(\\)))", 92 | "patterns": [ 93 | { 94 | "name": "keyword.other.dds.lf.comp.values", 95 | "match": "(?i)(\\b(GE|LE|NG|GT|NL|LT|NE|EQ)\\b)" 96 | }, 97 | { 98 | "name": "constant.numeric.dds.lf", 99 | "match": "\\b([0-9]+)\\b" 100 | } 101 | ] 102 | } 103 | ] 104 | }, 105 | "strings": { 106 | "name": "string.quoted.single.dds.lf", 107 | "begin": "'", 108 | "end": "'", 109 | "patterns": [ 110 | { 111 | "name": "keyword.other.dds.lf.spec", 112 | "match": "(?i)(?<=^.{5})[A]" 113 | } 114 | ] 115 | } 116 | }, 117 | "scopeName": "source.dds.lf" 118 | } -------------------------------------------------------------------------------- /syntaxes/cmd.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "CMD", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#support" 10 | }, 11 | { 12 | "include": "#variables" 13 | }, 14 | { 15 | "include": "#constants" 16 | }, 17 | { 18 | "include": "#keywords" 19 | }, 20 | { 21 | "include": "#strings" 22 | } 23 | ], 24 | "repository": { 25 | "comments": { 26 | "patterns": [ 27 | { 28 | "name": "comment.line.cmd", 29 | "begin": "(\\/\\*)", 30 | "end": "(\\*\\/)" 31 | } 32 | ] 33 | }, 34 | "constants": { 35 | "patterns": [ 36 | { 37 | "name": "constant.language.cmd", 38 | "match": "(?i)[*]\\b(IN)([0-9]{0,2})\\b" 39 | }, 40 | { 41 | "name": "constant.numeric.cmd", 42 | "match": "(\\b[0-9]+)|([0-9]*[.][0-9]*)" 43 | }, 44 | { 45 | "name": "constant.language.cmd", 46 | "match": "[*][a-zA-Z][a-zA-Z0-9]*" 47 | } 48 | ] 49 | }, 50 | "keywords": { 51 | "patterns": [ 52 | { 53 | "name": "keyword.control.cmd.label", 54 | "match": "^\\s*[a-zA-Z_@#$§ÆØÅÄ֣ѥàÐŞİ][a-zA-Z0-9_@#$§ÆØÅÄ֣ѥàÐŞİ]*:" 55 | }, 56 | { 57 | "name": "keyword.other.cmd", 58 | "match": "(?i)\\b(QUAL|PMTCTL|PARM|ELEM|DEP|CMD)\\b" 59 | }, 60 | { 61 | "name": "keyword.other.cmd", 62 | "match": "(?i)[*](CAT|TCAT|BCAT|AND|OR|NOT|EQ|GT|LT|GE|LE|NE|NG|NL)" 63 | }, 64 | { 65 | "name": "keyword.other.cmd", 66 | "match": "(([\\|](\\||>|<))|\\+|\\-|\\*|\\/|>=|<=|=|>|<|:)" 67 | } 68 | ] 69 | }, 70 | "strings": { 71 | "patterns": [ 72 | { 73 | "name": "string.other.cmd.hex", 74 | "begin": "(?i)x'", 75 | "end": "'" 76 | }, 77 | { 78 | "name": "string.quoted.single.cmd", 79 | "begin": "'", 80 | "end": "'", 81 | "patterns": [ 82 | { 83 | "name": "constant.character.escape.cmd", 84 | "match": "\\\\." 85 | } 86 | ] 87 | } 88 | ] 89 | }, 90 | "support": { 91 | "patterns": [ 92 | { 93 | "name": "support.function.cmd", 94 | "match": "[a-zA-Z_][a-zA-Z0-9_]*(?=\\()" 95 | } 96 | ] 97 | }, 98 | "variables": { 99 | "patterns": [ 100 | { 101 | "name": "variable.parameter.cmd", 102 | "match": "[&][a-zA-Z_@#$§ÆØÅÄ֣ѥàÐŞİ][a-zA-Z0-9_@#$§ÆØÅÄ֣ѥàÐŞİ]*" 103 | } 104 | ] 105 | } 106 | }, 107 | "scopeName": "source.cmd" 108 | } -------------------------------------------------------------------------------- /tests/general/test.dspf: -------------------------------------------------------------------------------- 1 | A*%%TS SD 20191211 003314 OTTEB REL-V7R3M0 5770-WDS 2 | A*%%EC 3 | A DSPSIZ(24 80 *DS3) 4 | A INDARA 5 | A R ALDR001 6 | A*%%TS SD 20191211 003314 OTTEB REL-V7R3M0 5770-WDS 7 | A CA03(03 'EXIT') 8 | A CA05(05 'REFRESH') 9 | A CA12(12 'CANCEL') 10 | A* 11 | A 2 4DATE 12 | A EDTCDE(Y) 13 | A 3 4TIME 14 | A 4 4USER 15 | A* 16 | A 2 29'Anilist Search' 17 | A 3 23'https://graphql.anilist.co' 18 | A 4 27'Barrett Otte 2019' 19 | A* 20 | A ALDONAME 18A O 6 53 21 | A ALDOURL 32A O 7 43 22 | A 10 5'Username ...' 23 | A ALDIUSRNM 18A B 10 18CHECK(LC) 24 | A 13 5'Id .........' 25 | A ALDOID 10A O 13 18 26 | A 15 5'Hours' 27 | A 18 41'+-----------------+---------------- 28 | A +' 29 | A 16 5'watched ....' 30 | A ALDOHOURS 10A O 16 18 31 | A 8 41'+-----------------+---------------- 32 | A +' 33 | A 9 41'!' 34 | A 9 59'!' 35 | A 9 75'!' 36 | A 10 41'!' 37 | A 10 43'Completed:' 38 | A ALDOLCOMP 4A O 10 54 39 | A 13 43'Dropped:' 40 | A ALDOLDROP 4A O 13 54 41 | A 16 43'Planned:' 42 | A ALDOLPLAN 4A O 16 54 43 | A 17 41'!' 44 | A 16 41'!' 45 | A 15 41'!' 46 | A 14 41'!' 47 | A 13 41'!' 48 | A 12 41'!' 49 | A 11 41'!' 50 | A 10 59'!' 51 | A 10 61'Current:' 52 | A ALDOLCURR 4A O 10 70 53 | A 13 61'Paused:' 54 | A ALDOLPAUS 4A O 13 70 55 | A 16 61'Repeat:' 56 | A ALDOLREPT 4A O 16 70 57 | A 11 59'!' 58 | A 12 59'!' 59 | A 13 59'!' 60 | A 14 59'!' 61 | A 15 59'!' 62 | A 16 59'!' 63 | A 17 59'!' 64 | A 10 75'!' 65 | A 11 75'!' 66 | A 12 75'!' 67 | A 13 75'!' 68 | A 14 75'!' 69 | A 15 75'!' 70 | A 16 75'!' 71 | A 17 75'!' 72 | A* 73 | A ALDOERROR 30A O 20 22 74 | A 22 11'F3=Exit' 75 | A 22 31'F5=Refresh' 76 | A 22 53'F12=Cancel' -------------------------------------------------------------------------------- /tests/general/test.clp: -------------------------------------------------------------------------------- 1 | /* https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/rbam6/datearith.htm */ 2 | /* Calculate new date from current system date. Pass negative */ 3 | /* number to subtract, positive number to add */ 4 | /* */ 5 | /* The first parameter is a character 8 date in YYYYMMDD format */ 6 | /* or the special value *CURRENT */ 7 | /* */ 8 | /* The second parameter is a decimal value for the number of days */ 9 | /* to adjust the first parameter by */ 10 | /* */ 11 | /* Test cases: CALL CALCDATE (*CURRENT -5) */ 12 | /* CALL CALCDATE (*CURRENT 5) */ 13 | /* CALL CALCDATE ('20030225' -90) */ 14 | /* CALL CALCDATE ('30020228' 90) */ 15 | /* */ 16 | /* There is no error handling in this sample, so make sure the */ 17 | /* input dates are valid (that is, no 20031325). The valid date */ 18 | /* date range is Oct 14 1582 to Dec 31 9999 */ 19 | /* */ 20 | PGM PARM(&curdate &DAYSTOCHG) 21 | DCL VAR(&CURDATE) TYPE(*CHAR) LEN(8) 22 | DCL VAR(&DAYSTOCHG) TYPE(*DEC) LEN(15 5) 23 | DCL VAR(&DATETIME) TYPE(*CHAR) LEN(17) 24 | DCL VAR(&DATE) TYPE(*CHAR) LEN(8) 25 | DCL VAR(&LILDATEINT) TYPE(*CHAR) LEN(4) 26 | DCL VAR(&LILDATEDEC) TYPE(*DEC) LEN(10 0) 27 | DCL VAR(&ERRCOD) TYPE(*CHAR) LEN(4) + 28 | VALUE(X'00000000') 29 | DCL VAR(&MSG) TYPE(*CHAR) LEN(50) 30 | LABEL1: 31 | IF COND(&CURDATE = '*CURRENT') THEN(DO) 32 | CALL PGM(QWCCVTDT) PARM('*CURRENT' ' ' '*YYMD' + 33 | &DATETIME &ERRCOD) /* Get current system + 34 | date and time in YYYYMMDD */ 35 | CHGVAR VAR(&DATE) VALUE(%SST(&DATETIME 1 8)) /* Get + 36 | just the date portion */ 37 | ENDDO 38 | ELSE CMD(CHGVAR VAR(&DATE) VALUE(&CURDATE)) /* + 39 | Use the date provided */ 40 | CALLPRC PRC(CEEDAYS) PARM(&DATE 'YYYYMMDD' + 41 | &LILDATEINT *OMIT) /* Get Lilian date for + 42 | current date */ 43 | CHGVAR VAR(&LILDATEDEC) VALUE(%BIN(&LILDATEINT)) /* + 44 | Get Lilian date in decimal format */ 45 | CHGVAR VAR(&LILDATEDEC) VALUE(&LILDATEDEC + + 46 | &DAYSTOCHG) /* Adjust specified number + 47 | of days */ 48 | CHGVAR VAR(%BIN(&LILDATEINT)) VALUE(&LILDATEDEC) /* + 49 | Get Lilian date in integer format */ 50 | CALLPRC PRC(CEEDATE) PARM(&LILDATEINT 'YYYYMMDD' + 51 | &DATE *OMIT) /* Return calculated date in + 52 | YYYYMMDD format */ 53 | CHGVAR VAR(&MSG) VALUE('The new date is ' *CAT &DATE) 54 | SNDPGMMSG MSG(&MSG) TOPGMQ(*EXT) 55 | END: 56 | ENDPGM -------------------------------------------------------------------------------- /syntaxes/dds.icff.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "DDS.ICFF", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#gutter" 16 | }, 17 | { 18 | "include": "#strings" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.dds.icff", 26 | "match": "^.{5}(.)(\\*).*" 27 | } 28 | ] 29 | }, 30 | "gutter": { 31 | "patterns": [ 32 | { 33 | "name": "comment.gutter", 34 | "match": "^.{5}" 35 | } 36 | ] 37 | }, 38 | "constants": { 39 | "patterns": [ 40 | { 41 | "name": "constant.language.dds.icff", 42 | "match": "(\\*)[a-zA-Z][a-zA-Z0-9]*" 43 | }, 44 | { 45 | "name": "constant.language.dds.icff.andor", 46 | "match": "(?i)(?<=^.{5}(A|\\s).{0})(A|O)" 47 | }, 48 | { 49 | "name": "constant.language.dds.icff.n01", 50 | "match": "(?i)(?<=^.{5}(A|\\s).{1})(N|\\s)[0-9]{2}" 51 | }, 52 | { 53 | "name": "constant.language.dds.icff.n02", 54 | "match": "(?i)(?<=^.{5}(A|\\s).{4})(N|\\s)[0-9]{2}" 55 | }, 56 | { 57 | "name": "constant.language.dds.icff.n03", 58 | "match": "(?i)(?<=^.{5}(A|\\s).{7})(N|\\s)[0-9]{2}" 59 | }, 60 | { 61 | "name": "constant.language.dds.icff.nameType", 62 | "match": "(?i)(?<=^.{5}(A|\\s).{10})(R|H)" 63 | }, 64 | { 65 | "name": "constant.language.dds.icff.ref", 66 | "match": "(?i)(?<=^.{5}(A|\\s).{22})(R)" 67 | }, 68 | { 69 | "name": "constant.language.dds.icff.len", 70 | "match": "(?i)(?<=^.{5}(A|\\s).{23})[0-9|\\s]{5}" 71 | }, 72 | { 73 | "name": "constant.language.dds.icff.dataType", 74 | "match": "(?i)(?<=^.{5}(A|\\s).{28})(P|S|B|F|A|O)" 75 | }, 76 | { 77 | "name": "constant.language.dds.icff.decpos", 78 | "match": "(?i)(?<=^.{5}(A|\\s).{29})[0-9|\\s]{2}" 79 | }, 80 | { 81 | "name": "constant.language.dds.icff.usage", 82 | "match": "(?i)(?<=^.{5}(A|\\s).{31})(B|P)" 83 | }, 84 | { 85 | "name": "constant.language.dds.icff.locline", 86 | "match": "(?i)(?<=^.{5}(A|\\s).{32})([0-9]|\\s){3}" 87 | }, 88 | { 89 | "name": "constant.numeric.dds.icff", 90 | "match": "\\b([0-9]+)\\b" 91 | } 92 | ] 93 | }, 94 | "keywords": { 95 | "patterns": [ 96 | { 97 | "name": "keyword.other.dds.icff.spec", 98 | "match": "(?i)(?<=^.{5})[A]" 99 | }, 100 | { 101 | "name": "keyword.other.dds.icff", 102 | "match": "\\+" 103 | }, 104 | { 105 | "name": "keyword.other.dds.icff.func", 106 | "match": "((?i)(C(A|F)))[0-9]{2}" 107 | }, 108 | { 109 | "name": "keyword.other.dds.icff.funcs", 110 | "match": "(?i)(?<=(.{44}))(VARLEN|VARBUFMGT|TNSSYNLVL|TIMER|TEXT|SYNLVL|SUBDEV|SECURITY|RSPCONFIRM|RQSWRT|REFFLD|REF|RECID|RCVTRNDRND|RCVTKCMT|RCVROLLB|RCVNEGRSP|RCVFMH|RCVFAIL|RCVENDGRP|RCVDETACH|RCVCTLDTA|RCVCONFIRM|RCVCANCEL|PRPCMT|NEGRSP|INVITE|INDTXT|INDARA|FRCDTA|FMTNAME|FMH|FLTPCN|FAIL|EVOKE|EOS|ENDGRP|DFREVOKE|DETACH|CTLDTA|CONFIRM|CNLINVITE|CANCEL|ALWWRT|ALIAS)\\b" 111 | }, 112 | { 113 | "name": "keyword.other.dds.icff.funcs", 114 | "match": "\\b(?i)(CMP|CLRL|SFL)\\b" 115 | } 116 | ] 117 | }, 118 | "strings": { 119 | "name": "string.quoted.single.dds.icff", 120 | "begin": "'", 121 | "end": "'", 122 | "patterns": [ 123 | { 124 | "name": "keyword.other.dds.icff.spec", 125 | "match": "(?i)(?<=^.{5})[A]" 126 | } 127 | ] 128 | } 129 | }, 130 | "scopeName": "source.dds.icff" 131 | } -------------------------------------------------------------------------------- /syntaxes/dds.prtf.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "DDS.PRTF", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#gutter" 16 | }, 17 | { 18 | "include": "#strings" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.dds.prtf", 26 | "match": "^.{5}(.)(\\*).*" 27 | } 28 | ] 29 | }, 30 | "gutter": { 31 | "patterns": [ 32 | { 33 | "name": "comment.gutter", 34 | "match": "^.{5}" 35 | } 36 | ] 37 | }, 38 | "constants": { 39 | "patterns": [ 40 | { 41 | "name": "constant.language.dds.prtf", 42 | "match": "(\\*)[a-zA-Z][a-zA-Z0-9]*" 43 | }, 44 | { 45 | "name": "constant.language.dds.prtf.andor", 46 | "match": "(?i)(?<=^.{5}(A|\\s).{0})(A|O)" 47 | }, 48 | { 49 | "name": "constant.language.dds.prtf.n01", 50 | "match": "(?i)(?<=^.{5}(A|\\s).{1})(N|\\s)[0-9]{2}" 51 | }, 52 | { 53 | "name": "constant.language.dds.prtf.n02", 54 | "match": "(?i)(?<=^.{5}(A|\\s).{4})(N|\\s)[0-9]{2}" 55 | }, 56 | { 57 | "name": "constant.language.dds.prtf.n03", 58 | "match": "(?i)(?<=^.{5}(A|\\s).{7})(N|\\s)[0-9]{2}" 59 | }, 60 | { 61 | "name": "constant.language.dds.prtf.nameType", 62 | "match": "(?i)(?<=^.{5}(A|\\s).{10})R" 63 | }, 64 | { 65 | "name": "constant.language.dds.prtf.ref", 66 | "match": "(?i)(?<=^.{5}(A|\\s).{22})R" 67 | }, 68 | { 69 | "name": "constant.language.dds.prtf.len", 70 | "match": "(?i)(?<=^.{5}(A|\\s).{23})[0-9|\\s]{5}" 71 | }, 72 | { 73 | "name": "constant.language.dds.prtf.dataType", 74 | "match": "(?i)(?<=^.{5}(A|\\s).{28})(A|F|G|L|O|S|T|Z)" 75 | }, 76 | { 77 | "name": "constant.language.dds.prtf.decpos", 78 | "match": "(?i)(?<=^.{5}(A|\\s).{29})[0-9|\\s]{2}" 79 | }, 80 | { 81 | "name": "constant.language.dds.prtf.usage", 82 | "match": "(?i)(?<=^.{5}(A|\\s).{31})O" 83 | }, 84 | { 85 | "name": "constant.language.dds.prtf.locline", 86 | "match": "(?i)(?<=^.{5}(A|\\s).{32})([0-9]|\\s|\\+){3}" 87 | }, 88 | { 89 | "name": "constant.language.dds.prtf.locpos", 90 | "match": "(?i)(?<=^.{5}(A|\\s).{35})([0-9]|\\s|\\+){3}" 91 | }, 92 | { 93 | "name": "constant.numeric.dds.prtf", 94 | "match": "\\b([0-9]+)\\b" 95 | } 96 | ] 97 | }, 98 | "keywords": { 99 | "patterns": [ 100 | { 101 | "name": "keyword.other.dds.prtf.spec", 102 | "match": "(?i)(?<=^.{5})[A]" 103 | }, 104 | { 105 | "name": "keyword.other.dds.prtf", 106 | "match": "\\+" 107 | }, 108 | { 109 | "name": "keyword.other.dds.prtf.func", 110 | "match": "((?i)(C(A|F)))[0-9]{2}" 111 | }, 112 | { 113 | "name": "keyword.other.dds.prtf.funcs", 114 | "match": "(?i)(?<=(.{44}))(ZFOLD|UNISCRIPT|UNDERLINE|TXTRTT|TRNSPY|TIMSEP|TIMFMT|TIME|TEXT|STRPAGGRP|STAPLE|SPACEB|SPACEA|SKIPB|SKIPA|RELPOS|REFFLD|REF|PRTQLTY|POSITION|PAGSEG|PAGRTT|PAGNBR|OVERLAY|OUTBIN|MSGCON|LPI|LINE|INVMMAP|INVDTAMAP|INDTXT|INDARA|HIGHLIGHT|GDF|FORCE|FONTNAME|FONT|FNTCHRSET|FLTPCN|FLTFIXDEC|ENDPAGGRP|ENDPAGE|EDTWRD|EDTCDE|DUPLEX|DTASTMCMD|DRAWER|DOCIDXTAG|DLTEDT|DFT|DFNCHR|DATSEP|DATFMT|DATE|CVTDTA|CPI|COLOR|CHRSIZ|CHRID|CDEFNT|BOX|BLKFOLD|BARCODE|ALIAS|AFPRSC)\\b" 115 | } 116 | ] 117 | }, 118 | "strings": { 119 | "name": "string.quoted.single.dds.prtf", 120 | "begin": "'", 121 | "end": "'", 122 | "patterns": [ 123 | { 124 | "name": "keyword.other.dds.prtf.spec", 125 | "match": "(?i)(?<=^.{5})[A]" 126 | } 127 | ] 128 | } 129 | }, 130 | "scopeName": "source.dds.prtf" 131 | } -------------------------------------------------------------------------------- /dev/rpg400/notes.rpg: -------------------------------------------------------------------------------- 1 | C* Hello world 2 | C MOVEL'HELLO' HELLO 11 3 | C MOVE 'WORLD' HELLO 4 | C HELLO DSPLY WAIT 1 5 | C SETON LR Done program! 6 | /EJECT 7 | 8 | 9 | ..... *. 1 ...+... 2 ...+... 3 ...+... 4 ...+... 5 ...+... 6 ...+... 7 ...+... 8 10 | 11 | .....CL0N01N02N03Factor1+++OpcdeFactor2+++ResultLenDHHiLoEqComments++++ 12 | 13 | C* HELLO WORLD 14 | C MOVEL'HELLO' HELLO 11 15 | C MOVE 'WORLD' HELLO 16 | C HELLO DSPLY WAIT 1 17 | C SETON LR ALL DONE 18 | 19 | 20 | .....FFilenameIPEAF....RlenLK1AIOvKlocEDevice+......KExit++Entry+A....U1........ 21 | 22 | 23 | ******* RPG/400 ******* 24 | 25 | * Opcodes 26 | 27 | ACQ Acquire 28 | ADD Add 29 | AND And 30 | BEGSR Begin subroutine 31 | BITOF Set bits off 32 | BITON Set bits on 33 | CAB Compare and branch 34 | CALL Call a program 35 | CAS Conditionally invoke subroutine 36 | CAT Concatenate two character strings 37 | CHAIN Random retrieval from a file 38 | CHECK Check characters 39 | CHEKR Check characters reverse 40 | CLEAR Clear 41 | CLOSE Close files 42 | COMIT Commit 43 | COMP Compare 44 | DEBUG Debug function 45 | DEFN Field definition 46 | DELET Delete record 47 | DIV Divide 48 | DO Do loop begin 49 | DOU Do until loop begin 50 | DOW Do while loop begin 51 | DSPLY Display function 52 | DUMP Program dump 53 | ELSE Else 54 | END End a Group 55 | ENDSR End of Subroutine 56 | EXCPT Calculation Time Output 57 | EXFMT Write/Then Read Format 58 | EXSR Invoke Subroutine 59 | FEOD Force End of Data 60 | FORCE Force a Certain File to Be Read Next Cycle 61 | FREE Deactivate a Program 62 | GOTO Go To 63 | IF If 64 | IN Retrieve a Data Area 65 | ITER Iterate 66 | KFLD Define Parts of a Key 67 | KLIST Define a Composite Key 68 | LEAVE Leave a Do Group 69 | LOKUP Look Up 70 | MHHZO Move High to High Zone 71 | MHLZO Move High to Low Zone 72 | MLHZO Move Low to High Zone 73 | MLLZO Move Low to Low Zone 74 | MOVE Move 75 | MOVEA Move Array 76 | MOVEL Move Left 77 | MULT Multiply 78 | MVR Move Remainder 79 | NEXT Next 80 | OCUR Set/Get Occurrence of a Data Structure 81 | OPEN Open File for Processing 82 | OR Or 83 | OTHER Otherwise Select 84 | OUT Write a Data Area 85 | PARM Identify Parameters 86 | PLIST Identify a Parameter List 87 | POST Post 88 | READ Read a Record 89 | READC Read Next Changed Record 90 | READE Read Equal Key 91 | READP Read Prior Record 92 | REDPE Read Prior Equal 93 | REL Release 94 | RESET Reset 95 | RETRN Return to Caller 96 | ROLBK Roll Back 97 | SCAN Scan Character String 98 | SELEC Begin a Select Group 99 | SETGT Set Greater Than 100 | SETLL Set Lower Limit 101 | SETOF Set Off 102 | SETON Set On 103 | SHTDN Shut Down 104 | SORTA Sort an Array 105 | SQRT Square Root 106 | SUB Subtract 107 | SUBST Substring 108 | TAG Tag 109 | TESTB Test Bit 110 | TESTN Test Numeric 111 | TESTZ Test Zone 112 | TIME Time of Day 113 | UNLCK Unlock a Data Area or Release a Record 114 | UPDAT Modify Existing Record 115 | WH When True Then Select 116 | WRITE Create New Records 117 | XFOOT Summing the Elements of an Array 118 | XLATE Translate 119 | Z-ADD Zero and Add 120 | Z-SUB Zero and Subtract 121 | 122 | 123 | * Relational Operators 124 | GT Greater than 125 | LT Less than 126 | EQ Equal to 127 | NE Not equal to 128 | GE Greater than or equal to 129 | LE Less than or equal to 130 | 131 | 132 | * Constants 133 | *BLANK 134 | *BLANKS 135 | *ZERO 136 | *ZEROS 137 | *HIVAL 138 | *LOVAL 139 | *ALL 140 | *ON 141 | *OFF 142 | *DATE 143 | UDATE 144 | *MONTH 145 | UMONTH 146 | *DAY 147 | UDAY 148 | *YEAR 149 | UYEAR 150 | *CANCL 151 | *DETC 152 | *DETL 153 | *GETIN 154 | *INIT 155 | *OFL 156 | *TERM 157 | *TOTC 158 | *TOTL 159 | *DEFN 160 | *ENTRY 161 | *INZSR 162 | *LDA 163 | *LIKE 164 | *LOCK 165 | *NAMVAR 166 | *OFF 167 | *ON 168 | *PDA 169 | *PSSR 170 | *FILE 171 | *EQUATE 172 | *PLACE 173 | 174 | -------------------------------------------------------------------------------- /tests/issues/136.cmd: -------------------------------------------------------------------------------- 1 | cmd prompt( 'Variant characters in identifiers' ) 2 | 3 | parm &@te@st@ *char 1 4 | parm &#te#st# *char 1 5 | parm &$te$st$ *char 1 6 | 7 | parm &qualified qual@#$ prompt( 'Object' ) 8 | qual@#$: qual *name 10 9 | qual *name 10 prompt( 'Library' ) 10 | 11 | /* note: double click doesn't select full identifier */ 12 | /* but, single clicking highlights full identifier */ 13 | /* I guess that's the correct behavior? */ 14 | 15 | /* Additional variants: https://docs.google.com/spreadsheets/d/1J4yEGkfhtmACfdDVyD2XNJe0jjrIK77Um6-wsvW0etM/edit?usp=sharing */ 16 | 17 | /* CCSID 273 (Austria and Germany) */ 18 | parm &@te@st@ *char 1 19 | parm &#te#st# *char 1 20 | parm &$te$st$ *char 1 21 | 22 | parm &qualified qual@#$ prompt( 'Object' ) 23 | qual@#$: qual *name 10 24 | qual *name 10 prompt( 'Library' ) 25 | 26 | /* CCSID 277 (Denmark and Norway) */ 27 | parm &ØteØstØ *char 1 28 | parm &ÆteÆstÆ *char 1 29 | parm &ÅteÅstÅ *char 1 30 | 31 | parm &qualified qualØÆÅ prompt( 'Object' ) 32 | qualØÆÅ: qual *name 10 33 | qual *name 10 prompt( 'Library' ) 34 | 35 | /* CCSID 278 (Finland and Sweden) */ 36 | parm &ÖteÖstÖ *char 1 37 | parm &ÄteÄstÄ *char 1 38 | parm &ÅteÅstÅ *char 1 39 | 40 | parm &qualified qualÖÄÅ prompt( 'Object' ) 41 | qualÖÄÅ: qual *name 10 42 | qual *name 10 prompt( 'Library' ) 43 | 44 | /* CCSID 280 (Italy) */ 45 | parm &§te§st§ *char 1 46 | parm &£te£st£ *char 1 47 | parm &$te$st$ *char 1 48 | 49 | parm &qualified qual§£$ prompt( 'Object' ) 50 | qual§£$: qual *name 10 51 | qual *name 10 prompt( 'Library' ) 52 | 53 | /* CCSID 284 (Spain and Latin America) */ 54 | parm &@te@st@ *char 1 55 | parm &ÑteÑstÑ *char 1 56 | parm &$te$st$ *char 1 57 | 58 | parm &qualified qual@Ñ$ prompt( 'Object' ) 59 | qual@Ñ$: qual *name 10 60 | qual *name 10 prompt( 'Library' ) 61 | 62 | /* CCSID 285 (Ireland and the United Kingdom) */ 63 | parm &@te@st@ *char 1 64 | parm &#te#st# *char 1 65 | parm &£te£st£ *char 1 66 | 67 | parm &qualified qual@#£ prompt( 'Object' ) 68 | qual@#£: qual *name 10 69 | qual *name 10 prompt( 'Library' ) 70 | 71 | /* CCSID 290 (Japan (katakana)) */ 72 | parm &@te@st@ *char 1 73 | parm &#te#st# *char 1 74 | parm &¥te¥st¥ *char 1 75 | 76 | parm &qualified qual@#¥ prompt( 'Object' ) 77 | qual@#¥: qual *name 10 78 | qual *name 10 prompt( 'Library' ) 79 | 80 | /* CCSID 297 (France) */ 81 | parm &àteàstà *char 1 82 | parm &£te£st£ *char 1 83 | parm &$te$st$ *char 1 84 | 85 | parm &qualified qualà£$ prompt( 'Object' ) 86 | qualà£$: qual *name 10 87 | qual *name 10 prompt( 'Library' ) 88 | 89 | /* CCSID 423 (Greece) */ 90 | parm &§te§st§ *char 1 91 | parm &£te£st£ *char 1 92 | parm &$te$st$ *char 1 93 | 94 | parm &qualified qual§£$ prompt( 'Object' ) 95 | qual§£$: qual *name 10 96 | qual *name 10 prompt( 'Library' ) 97 | 98 | /* CCSID 871 (Iceland) */ 99 | parm &ÐteÐstÐ *char 1 100 | parm &#te#st# *char 1 101 | parm &$te$st$ *char 1 102 | 103 | parm &qualified qualÐ#$ prompt( 'Object' ) 104 | qualÐ#$: qual *name 10 105 | qual *name 10 prompt( 'Library' ) 106 | 107 | /* CCSID 905 (Turkey - Latin-3) */ 108 | parm &ŞteŞstŞ *char 1 109 | parm &ÖteÖstÖ *char 1 110 | parm &İteİstİ *char 1 111 | 112 | parm &qualified qualŞÖİ prompt( 'Object' ) 113 | qualŞÖİ: qual *name 10 114 | qual *name 10 prompt( 'Library' ) 115 | -------------------------------------------------------------------------------- /tests/general/bfint.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // Basic BF Interpreter in fully free RPGLE 3 | 4 | ctl-opt main(main); 5 | ctl-opt option(*srcstmt:*nodebugio:*nounref) dftactgrp(*no); 6 | 7 | dcl-c MEMSIZE 30000; 8 | dcl-c PGMSIZE 4096; 9 | dcl-c BUFFSIZE 128; 10 | 11 | dcl-s memory int(3) dim(MEMSIZE) inz(*zeros); 12 | dcl-s result varchar(BUFFSIZE) inz(*blanks); 13 | dcl-s pgm varchar(PGMSIZE); 14 | dcl-s insPtr int(5) inz(1); 15 | dcl-s memPtr int(5) inz(1); 16 | dcl-s outPtr int(5) inz(1); 17 | 18 | 19 | dcl-pr main extpgm('BFINT'); 20 | *n char(PGMSIZE); 21 | *n char(BUFFSIZE); 22 | end-pr; 23 | 24 | 25 | dcl-proc main; 26 | dcl-pi *n; 27 | bfpgm char(PGMSIZE); 28 | outBuffer char(BUFFSIZE); 29 | end-pi; 30 | 31 | dcl-s ins char(1) inz(''); 32 | 33 | monitor; 34 | memory(*) = 1; 35 | pgm = sanitize(bfpgm); 36 | 37 | for insPtr = 1 to %len(pgm); 38 | ins = getInstruction(); 39 | 40 | select; 41 | when (ins = '>'); 42 | moveRight(); 43 | when (ins = '<'); 44 | moveLeft(); 45 | when (ins = '+'); 46 | increment(); 47 | when (ins = '-'); 48 | decrement(); 49 | when (ins = '.'); 50 | output(); 51 | when (ins = ','); 52 | input(); 53 | when (ins = '['); 54 | jumpFwd(); 55 | when (ins = ']'); 56 | jumpBack(); 57 | other; 58 | // ignore bad instructions 59 | endsl; 60 | endfor; 61 | 62 | on-error; 63 | dsply ('Fatal error occurred interpreting BF source.'); 64 | return; 65 | endmon; 66 | 67 | on-exit; 68 | outBuffer = result; 69 | *inlr = *on; 70 | return; 71 | end-proc; 72 | 73 | 74 | // strip valid characters out of source 75 | dcl-proc sanitize; 76 | dcl-pi *n char(PGMSIZE); 77 | dirty char(PGMSIZE); 78 | end-pi; 79 | 80 | dcl-c valid '[]><+-.,'; 81 | dcl-s buffer char(PGMSIZE) inz(*blanks); 82 | dcl-s i int(5) inz(0); 83 | 84 | for i = 1 to %len(dirty); 85 | if %scan(%subst(dirty:i:1):valid) <> 0; 86 | %subst(buffer:i:1) = %subst(dirty:i:1); 87 | endif; 88 | endfor; 89 | 90 | return %trim(buffer); 91 | end-proc; 92 | 93 | 94 | // get current instruction at instruction pointer 95 | dcl-proc getInstruction; 96 | dcl-pi *n char(1) end-pi; 97 | 98 | return %subst(pgm:insPtr:1); 99 | end-proc; 100 | 101 | 102 | // increment memory pointer to next cell on the right 103 | dcl-proc moveRight; 104 | if memPtr = MEMSIZE; 105 | memPtr = 1; 106 | else; 107 | memPtr += 1; 108 | endif; 109 | end-proc; 110 | 111 | 112 | // decrement data pointer to next cell on the left 113 | dcl-proc moveLeft; 114 | if memPtr = 1; 115 | memPtr = MEMSIZE; 116 | else; 117 | memPtr -= 1; 118 | endif; 119 | end-proc; 120 | 121 | 122 | // increment byte at memory pointer 123 | dcl-proc increment; 124 | memory(memPtr) += 1; 125 | end-proc; 126 | 127 | 128 | // decrement byte at memory pointer 129 | dcl-proc decrement; 130 | memory(memPtr) -= 1; 131 | end-proc; 132 | 133 | 134 | // add byte at memory pointer to output buffer 135 | dcl-proc output; 136 | dcl-s memCell int(3) inz(*zeros); 137 | dcl-s outCell char(1) inz(*blanks); 138 | 139 | // check ASCII decimal => %char(%editc(memory(memPtr):'X')); 140 | memCell = memory(memPtr); 141 | 142 | exec SQL 143 | set :outCell = chr(:memCell - 1); 144 | 145 | %subst(result:outPtr:1) = outCell; 146 | outPtr += 1; 147 | end-proc; 148 | 149 | 150 | // input byte and store at memory pointer 151 | dcl-proc input; 152 | dcl-s c char(16) inz(*blanks); 153 | 154 | dsply 'INPUT: ' '' c; 155 | memory(memPtr) = %int(%subst(c:1:1)); 156 | end-proc; 157 | 158 | 159 | // jump instruction pointer forward to next instruction after matching ']' instruction 160 | dcl-proc jumpFwd; 161 | dcl-s depth int(5) inz(0); 162 | dcl-s ins char(1) inz(''); 163 | 164 | if memory(memPtr) = 1; 165 | insPtr += 1; 166 | ins = getInstruction(); 167 | 168 | dow depth > 0 or ins <> ']'; 169 | if ins = '['; 170 | depth += 1; 171 | elseif ins = ']'; 172 | depth -= 1; 173 | endif; 174 | 175 | insPtr += 1; 176 | ins = getInstruction(); 177 | enddo; 178 | endif; 179 | end-proc; 180 | 181 | 182 | // jump instruction pointer back to instruction after matching '[' instruction 183 | dcl-proc jumpBack; 184 | dcl-s depth int(5) inz(0); 185 | dcl-s ins char(1) inz(''); 186 | 187 | if memory(memPtr) <> 1; 188 | insPtr -= 1; 189 | ins = getInstruction(); 190 | 191 | dow depth > 0 or ins <> '['; 192 | if ins = ']'; 193 | depth += 1; 194 | elseif ins = '['; 195 | depth -= 1; 196 | endif; 197 | 198 | insPtr -= 1; 199 | ins = getInstruction(); 200 | enddo; 201 | 202 | insPtr -= 1; 203 | endif; 204 | end-proc; -------------------------------------------------------------------------------- /tests/issues/54.sqlrpgle: -------------------------------------------------------------------------------- 1 | **free 2 | // https://github.com/barrettotte/vscode-ibmi-languages/issues/54 3 | 4 | 5 | // Built in Global variables - https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafzgvars.htm 6 | Exec SQL 7 | CLIENT_HOST CLIENT_IPADDR CLIENT_PORT JOB_NAME PACKAGE_NAME PACKAGE_SCHEMA PACKAGE_VERSION 8 | PROCESS_ID ROUTINE_SCHEMA ROUTINE_SPECIFIC_NAME ROUTINE_TYPE SERVER_MODE_JOB_NAME THREAD_ID 9 | ; 10 | 11 | 12 | // Built in functions - https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafzch2func.htm 13 | // aggregate - https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafzcolfunc.htm 14 | // table - https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafztblfunc.htm 15 | // scalar - https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafzscale.htm 16 | // 17 | // went with generic function regex => match identifier and open parenthesis 18 | Exec SQL 19 | select myfunc(somefield) into :myds.myField 20 | from SOMELIB/MYPF 21 | where 1=1 22 | limit 10 23 | order by 1 desc 24 | ; 25 | 26 | 27 | // reserved schema names - https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafzresschem.htm 28 | // went with generic schema => identifier + (.|/) (object)? 29 | exec SQL 30 | QSYS2.TEST SYSCAT.TEST SYSFUN/TEST SYSIBM/TEST SYSIBMADM.TEST SYSPROC.TEST 31 | SYSPUBLIC/TEST SYSSTAT/TEST SYSTEM.TEST 32 | ; 33 | exec sql 34 | select * from QSYS2.SYSPARTITIONSTAT where SYSTEM_TABLE_SCHEMA='BOLIB'; 35 | 36 | exec sql 37 | select Mylib.myFunc(a.mfld) from MyOtherLib/mytable a; 38 | 39 | 40 | // reserved words => https://www.ibm.com/support/knowledgecenter/ssw_ibm_i_72/db2/rbafzwordsre.htm 41 | exec sql 42 | ABSENT ACCORDING ACCTNG ACTION ACTIVATE ADD ALIAS ALL ALLOCATE ALLOW ALTER AND ANY APPEND APPLNAME 43 | ARRAY ARRAY_AGG AS ASC ASENSITIVE ASSOCIATE AT ATOMIC ATTRIBUTES AUTHORIZATION AUTONOMOUS BEFORE 44 | BEGIN BETWEEN BINARY BIND BIT BUFFERPOOL BY CACHE CALL CALLED CARDINALITY CASE CAST CCSID CHAR 45 | CHARACTER CHECK CL CLOSE CLUSTER COLLECT COLLECTION COLUMN COMMENT COMMIT COMPACT COMPRESS CONCAT 46 | CONCURRENT CONDITION CONNECT CONNECT_BY_ROOT CONNECTION CONSTANT CONSTRAINT CONTAINS CONTENT 47 | CONTINUE COPY COUNT COUNT_BIG CREATE CREATEIN CROSS CUBE CURRENT CURRENT_DATE CURRENT_PATH 48 | CURRENT_SCHEMA CURRENT_SERVER CURRENT_TIME CURRENT_TIMESTAMP CURRENT_TIMEZONE CURRENT_USER CURSOR 49 | CYCLE DATA DATABASE DATAPARTITIONNAME DATAPARTITIONNUM DATE DAY DAYS DBINFO DBPARTITIONNAME 50 | DBPARTITIONNUM DB2GENERAL DB2GENRL DB2SQL DEACTIVATE DEALLOCATE DECLARE DEFAULT DEFAULTS DEFER DEFINE 51 | DEFINITION DELETE DELETING DENSERANK DENSE_RANK DESC DESCRIBE DESCRIPTOR DETERMINISTIC DIAGNOSTICS 52 | DISABLE DISALLOW DISCONNECT DISTINCT DO DOCUMENT DOUBLE DROP DYNAMIC EACH ELSE ELSEIF EMPTY ENABLE 53 | ENCODING ENCRYPTION END ENDING END-EXEC ENFORCED ERROR ESCAPE EVERY EXCEPT EXCEPTION EXCLUDING 54 | EXCLUSIVE EXECUTE EXISTS EXIT EXTEND EXTERNAL EXTRACT FENCED FETCH FIELDPROC FILE FINAL FOR FOREIGN 55 | FORMAT FREE FREEPAGE FROM FULL FUNCTION GBPCACHE GENERAL GENERATED GET GLOBAL GO GOTO GRANT GRAPHIC 56 | GROUP HANDLER HASH HASHED_VALUE HAVING HINT HOLD HOUR HOURS ID IDENTITY IF IGNORE IMMEDIATE IMPLICITLY 57 | IN INCLUDE INCLUDING INCLUSIVE INCREMENT INDEX INDEXBP INDICATOR INF INFINITY INHERIT INLINE INNER 58 | INOUT INSENSITIVE INSERT INSERTING INTEGRITY INTERSECT INTO IS ISOLATION ITERATE JAVA JOIN JSON_ARRAY 59 | JSON_ARRAYAGG JSON_EXISTS JSON_OBJECT JSON_OBJECTAGG JSON_QUERY JSON_TABLE JSON_VALUE KEEP KEY 60 | LABEL LANGUAGE LATERAL LEAVE LEFT LEVEL2 LIKE LIMIT LINKTYPE LISTAGG LOCAL LOCALDATE LOCALTIME 61 | LOCALTIMESTAMP LOCATION LOCATOR LOCK LOCKSIZE LOG LOGGED LONG LOOP MAINTAINED MASK MATCHED MATERIALIZED 62 | MAXVALUE MERGE MICROSECOND MICROSECONDS MINPCTUSED MINUTE MINUTES MINVALUE MIXED MODE MODIFIES MONTH 63 | MONTHS NAMESPACE NAN NATIONAL NCHAR NCLOB NESTED NEW NEW_TABLE NEXTVAL NO NOCACHE NOCYCLE NODENAME 64 | NODENUMBER NOMAXVALUE NOMINVALUE NONE NOORDER NORMALIZED NOT NULL NULLS NVARCHAR OBID OF OFFSET 65 | OLD OLD_TABLE OMIT ON ONLY OPEN OPTIMIZE OPTION OR ORDER ORDINALITY ORGANIZE OUT OUTER OVER OVERLAY 66 | OVERRIDING PACKAGE PADDED PAGE PAGESIZE PARAMETER PART PARTITION PARTITIONED PARTITIONING PARTITIONS 67 | PASSING PASSWORD PATH PCTFREE PERMISSION PIECESIZE PIPE PLAN POSITION PREPARE PREVVAL PRIMARY PRIOR 68 | PRIQTY PRIVILEGES PROCEDURE PROGRAM PROGRAMID QUERY RANGE RANK RCDFMT READ READS RECOVERY REFERENCES 69 | REFERENCING REFRESH REGEXP_LIKE RELEASE RENAME REPEAT RESET RESIGNAL RESTART RESULT RESULT_SET_LOCATOR 70 | RETURN RETURNING RETURNS REVOKE RID RIGHT ROLLBACK ROLLUP ROUTINE ROW ROWNUMBER ROW_NUMBER ROWS RRN RUN 71 | SAVEPOINT SBCS SCHEMA SCRATCHPAD SCROLL SEARCH SECOND SECONDS SECQTY SECURED SELECT SENSITIVE SEQUENCE 72 | SESSION SESSION_USER SET SIGNAL SIMPLE SKIP SNAN SOME SOURCE SPECIFIC SQL SQLID STACKED START STARTING 73 | STATEMENT STATIC STOGROUP SUBSTRING SUMMARY SYNONYM SYSTEM_USER TABLE TABLESPACE TABLESPACES THEN THREADSAFE 74 | TIME TIMESTAMP TO TRANSACTION TRANSFER TRIGGER TRIM TRIM_ARRAY TRUNCATE TYPE UNDO UNION UNIQUE UNIT 75 | UNNEST UNTIL UPDATE UPDATING URI USAGE USE USER USERID USING VALUE VALUES VARIABLE VARIANT VCAT VERSION 76 | VIEW VOLATILE WAIT WHEN WHENEVER WHERE WHILE WITH WITHIN WITHOUT WRAPPED WRAPPER WRITE WRKSTNNAME XMLAGG 77 | XMLATTRIBUTES XMLCAST XMLCOMMENT XMLCONCAT XMLDOCUMENT XMLELEMENT XMLFOREST XMLGROUP XMLNAMESPACES XMLPARSE 78 | XMLPI XMLROW XMLSERIALIZE XMLTABLE XMLTEXT XMLVALIDATE XSLTRANSFORM XSROBJECT YEAR YEARS YES ZONE 79 | -------------------------------------------------------------------------------- /syntaxes/mi.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "MI", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#strings" 16 | }, 17 | { 18 | "include": "#support" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.mi", 26 | "begin": "(\\/\\*)", 27 | "end": "(\\*\\/)" 28 | } 29 | ] 30 | }, 31 | "constants": { 32 | "patterns": [ 33 | { 34 | "name": "constant.language.mi", 35 | "match": "(?i)[*]\\b(IN)([0-9]{0,2})\\b" 36 | }, 37 | { 38 | "name": "constant.numeric.mi", 39 | "match": "(\\b[0-9]+)|([0-9]*[.][0-9]*)" 40 | }, 41 | { 42 | "name": "constant.language.mi", 43 | "match": "[*][a-zA-Z][a-zA-Z0-9]*" 44 | } 45 | ] 46 | }, 47 | "keywords": { 48 | "patterns": [ 49 | { 50 | "name": "keyword.control.mi.label", 51 | "match": "^\\s*[a-zA-Z_][a-zA-Z0-9_\\-]*:" 52 | }, 53 | { 54 | "name": "keyword.other.mi", 55 | "match": "\\b(?i)(YIELD|XORSTR|XOR|XLATWTDS|XLATEWT|XLATEMB|XLATEB1|XLATEB|XLATE|XFRLOCK|XCTL|WAITTIME|VERIFY|UNLOCKSL|UNLOCK|UNLKMTX|UNLCKTSL|TSTRPLC|TSTINLTH|TSTBUM|TSTBTS|TRIML|TESTULA|TESTTOBJ|TESTSUBSET|TESTRPL|TESTPTR|TESTPDC|TESTINTR|TESTEXCP|TESTEAU|TESTAU|TANH|TAN|SYNCSTG|SUBSPPFO|SUBSPP|SUBN|SUBLC|STSPPO|STPLLEN|SSCA|SNSEXCPD|STRNCPYNULLPAD|STRNCPYNULL|STRNCMPNULL|STRLENNULL|SINH|SIN|SIGEXCP|SETSPPO|SETSPPFP|SETSPPD|SETSPP|SETSPFP|SETIP|SETINVF|SETIEXIT|SETHSSMK|SETDPAT|SETDPADR|SETDP|SETCA|SETBTS|SETALLEN|SETACST|SEARCH|SCANX|SCANWC|SCAN|SCALE|RTX|RTNEXCP|RSLVSP|RSLVDP|RMVINXEN|RINZSTAT|RETTSADR|RETTHID|RETTHCNT|RETINVF|RETEXCPD|RETCA|REM|REALCHSS|QUANTIZEBV|QUANTIZEBE|PROPB|POWER|POPPAR8|POPPAR4|POPCNTB|POPCNT8|POPCNT4|PCOPTR2|PCOPTR|OVRPGATR|ORSTR|OR|OPM_PARM_CNT|OPM_PARM_ADDR|NPM_PARMLIST_ADDR|NOT|NOOPS|NOOP|NEG|MPYSUB|MPYADD|MULT|MODS2|MODS1|MODS|MODINVAU|MODINX|MODEXCPD|MODASA|MEMUSEHINT|MEMMOVE|MEMCPY|MEMCMP|MATUPID|MATUP|MATTODAT|MATSOBJ|MATS|MATSELLK|MATRMD|MATQMSGQ|MATQAT|MATPGMNM|MATPG|MVLICOPT|MATPRMTX|MATPRMSG|MATPRLK|MATPRECL|MATPRATR|MATPRAGP|MATPTRL|MATPTRIF|MATPTR|MATOBJLCK|MATMTX|MATMIF|MATMDATA|MATMATR1|MATMATR|MATJSAT|MATJPAT|MATJOBJ|MATJOAT|MATINVS|MATINVE|MATINVAT|MATINV|MATINAT|MATINXAT|MATEXCPD|MATDMPS|MATDRECL|MATBPGM|MATAUU|MATAUOBJ|MATAL|MATAU|MATAOL|MATHSAT|MATAGPAT|MATACTEX|MATACTAT|MATAGAT|LN|LOCKTSL|LOCKSL|LOCKMTX|LOCK|INVP|INSINXEN|INITEHCA|INCTS|INCT|INCD|GENUUID|FREHSSMK|FREHSS|FNDRINVN|FNDINXEN|STRCHRNULL|MEMCHR|FINDBYTE|EXTRMAG|EXTREXP|ECSCAN|EEXP|EXCHBY|ENSOBJ|ENQ|END|EDITPD|LBEDIT|EDIT|DIVREM|DIV|DESS|DESMTX|DESINX|DESHS|DEQWAIT|DEQ|DECTS|DECT|DECD|DCPDATA|DEACTPG|CVTTS|CVTT|CVTSC|CVTNC|CVTMC|CVTHC|CVTFPDF|CVTEFN|CVTDFFP|CVTD|CVTCS|CVTCN|CVTCM|CVTCH|CVTCB|CVTBC|CRTMTX|CRTINX|CRTHS|CNTLZ8|CNTLZ4|COT|COSH|COS|LBCPYNVR|LBCPYNV|CPYNV|STRCPYNULL|CPYHEXZZ|CPYHEXZN|CPYHEXNZ|CPYHEXNN|CPYECLAP|CPYBWP|CPYBRAP|CPYBRA|CPYBREP|CPYBO|CPYBOLAP|CPYBOLA|CPYBLAP|CPYBLA|CPYBBTL|CPYBBTA|CPYBYTES|CPYBTRLS|CPYBTRAS|CPYBTLLS|CPYBTL|CPYBTA|CPRDATA|CAT|CMPTOPAD|CMPSWP|CMPSW|CMPSPAD|CMPPTRT|CMPPTRE|CMPPTRA|CMPPSPAD|CMPNV|STRCMPNULL|CMPBRAP|CMPBRA|CMPBLAP|CMPBLA|CMF2|CMF1|CDD|CAI|COMSTR|CLRLKVAL|CLRINVF|CLRIEXIT|CLRBTS|CIPHER|CHKLKVAL|CALLPGMV|CALLI|CALLX|BITPERM|ATMCOR|ATMCAND|ATMCADD|ATANH|ATAN|ASIN|ACOS|ANDSTR|ANDCSTR|AND|ALCHSS|ADDSPP|ADDN|ADDLC|ACTPG|ACTBPGM)\\b" 56 | }, 57 | { 58 | "name": "keyword.other.mi", 59 | "match": "\\s+(?i)(MATCTX|B|CRTS|CTSD|CTD)\\b" 60 | }, 61 | { 62 | "name": "keyword.other.mi", 63 | "match": "\\b(?i)(ENTRY|DCL|PARM_LIST|PARM|PEND|EXT)\\b" 64 | }, 65 | { 66 | "name": "keyword.other.mi", 67 | "match": "\\b(([\\|](\\||>|<))|\\+|>=|<=|=|>|<|:)\\b" 68 | }, 69 | { 70 | "name": "keyword.other.mi", 71 | "match": "\\*" 72 | } 73 | ] 74 | }, 75 | "strings": { 76 | "patterns": [ 77 | { 78 | "name": "string.other.mi.hex", 79 | "begin": "(?i)x'", 80 | "end": "'" 81 | }, 82 | { 83 | "name": "string.quoted.single.mi", 84 | "begin": "('|\")", 85 | "end": "'|\"", 86 | "patterns": [ 87 | { 88 | "name": "constant.character.escape.mi", 89 | "match": "\\\\." 90 | } 91 | ] 92 | } 93 | ] 94 | }, 95 | "support": { 96 | "patterns": [ 97 | { 98 | "name": "support.type.mi", 99 | "match": "\\b(?i)(SPCPTR|SYSPTR|OL|DD)" 100 | }, 101 | { 102 | "name": "support.function.mi", 103 | "match": "\\b(?i)[A-Za-z]+\\s*(?=\\()" 104 | } 105 | ] 106 | } 107 | }, 108 | "scopeName": "source.mi" 109 | } -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # vscode-ibmi-languages 2 | 3 | Syntax highlighting for IBMi languages such as RPG, CL, DDS, MI, and RPGLE fixed/free. 4 | 5 | **Please consider downloading [code-for-ibmi](https://github.com/halcyon-tech/code-for-ibmi) to edit RPG, RPGLE, and CL directly in VS Code!** 6 | 7 | There's probably a few syntax bugs. Please submit a pull request or issue if you see something amiss. 8 | 9 | ## Contributors 10 | 11 | * [@barrettotte](https://github.com/barrettotte) 12 | * [@worksofliam](https://github.com/worksofliam) 13 | * [@chrjorgensen](https://github.com/chrjorgensen) 14 | * [@GajenderI](https://github.com/GajenderI) 15 | * [@lildude](https://github.com/lildude) 16 | * [@richardm90](https://github.com/richardm90) 17 | 18 | ## Features 19 | 20 | * Syntax highlighting for RPG III and RPG/400 - H,F,E,L,I,C,O specs 21 | * Syntax highlighting for Control Language (CL) 22 | * Syntax highlighting for Command Definition (CMD) 23 | * Syntax highlighting for UIM Panel Group (PNLGRP) 24 | * Syntax highlighting for DDS files - physical, logical, display, printer, and ICF 25 | * Syntax highlighting for Machine Interface (MI) 26 | * Syntax highlighting for RPGLE fixed - H,F,D,I,C,O,P specs 27 | * Syntax highlighting for RPGLE free 28 | * Syntax highlighting for embedded SQL in SQLRPG and SQLRPGLE 29 | * Support for a mix of RPGLE free and fixed format 30 | * Support for binder language 31 | * Support for DB2 SQL keywords in embedded SQL 32 | 33 | Last updated to **Fall 2023 PTF enhancements for 7.5 and 7.4** 34 | 35 | ## File Types (case insensitive) 36 | 37 | For each source type, I lumped legacy (system/38) source types together with the regular source types. 38 | 39 | | Extension(s) | Description | 40 | | ----------------------------- | ------------------ | 41 | | .cl, .clp, .clp38 .clle | Control Language (CL) | 42 | | .cmd | Command Definition (CMD) | 43 | | .pnlgrp | UIM Panel Group (PNLGRP) | 44 | | .dspf, .dspf38 | DDS Display file | 45 | | .icff | DDS ICF file | 46 | | .lf, .lf38 | DDS Logical file | 47 | | .pf, .pf38, .dds | DDS Physical file | 48 | | .prtf, .prtf38 | DDS Printer file | 49 | | .rpg, .rpg38, .sqlrpg | RPG/400 | 50 | | .rpgle, .sqlrpgle | RPGLE and SQLRPGLE | 51 | | .bnd | Binder Language | 52 | | .mi | Machine Interface (MI) | 53 | 54 | ## Screenshots 55 | 56 | See **screenshots/** for more examples of syntax highlighting. 57 | 58 | ### RPG/400 59 | 60 | ![RPG/400](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/rpg400.png) 61 | 62 | ### RPGLE Fixed Format 63 | 64 | ![RPGLE Fixed](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/rpglefixed.PNG) 65 | 66 | ### RPGLE Free Format 67 | 68 | ![RPGLE Free](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/rpglefree.PNG) 69 | 70 | ### RPGLE Free with Embedded SQL 71 | 72 | ![SQLRPGLE](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/sqlrpgle.PNG) 73 | 74 | ### Control Language (CL) 75 | 76 | ![CL](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/cl.png) 77 | 78 | ### Command (CMD) 79 | 80 | ![CL](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/cmd.png) 81 | 82 | ### UIM Panel Group (PNLGRP) 83 | 84 | ![CL](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/pnlgrp.png) 85 | 86 | ### Data Description Specification - Physical File (DDS) 87 | 88 | ![PF](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/pf.PNG) 89 | 90 | ### Machine Interface (MI) 91 | 92 | ![MI](https://raw.githubusercontent.com/barrettotte/vscode-ibmi-languages/master/screenshots/mi.PNG) 93 | 94 | ## Publishing 95 | 96 | ### VS Code Marketplace 97 | 98 | * `npm install -g vsce` 99 | * `vsce package` 100 | * `vsce publish -p VSCE_SECRET` 101 | 102 | ### OpenVSX 103 | 104 | This extension is also deployed to [Open VSX](https://open-vsx.org/extension/barrettotte/ibmi-languages) 105 | 106 | * `npx ovsx publish -p OPEN_VSX_SECRET` 107 | 108 | ## Changelog 109 | 110 | See [CHANGELOG.md](https://github.com/barrettotte/vscode-ibmi-languages/blob/master/CHANGELOG.md) 111 | 112 | ## Known Bugs / Future Improvements 113 | 114 | See [issues](https://github.com/barrettotte/vscode-ibmi-languages/issues). 115 | 116 | ## Featured In 117 | 118 | * 119 | * 120 | * 121 | 122 | ## References 123 | 124 | * Derived from an [existing RPG extension](https://github.com/NielsLiisberg/RPG-for-VSCode) 125 | * [Repo used to test older RPG](https://github.com/worksofliam/flight400) 126 | * [RPG/400](https://www.ibm.com/support/knowledgecenter/SSAE4W_9.6.0/com.ibm.etools.iseries.langref.doc/evferlsh02.htm#ToC) 127 | * [RPG II, RPG III, and RPG/400](https://isbnsearch.org/isbn/0878352465) 128 | * [Regex tool](https://regexr.com/) 129 | * [VS Code Language extensions](https://code.visualstudio.com/api/language-extensions/overview) 130 | * [IBM List of CL Commands](https://www.ibm.com/docs/en/i/7.5?topic=language-alphabetic-list-cl-commands-by-command-name) 131 | 132 | 133 | 134 | ## Hints & Tips 135 | 136 | 137 | ### tmLanguage Scope Names 138 | 139 | The colours used in VS Code are determined by the scope names assigned in the 140 | relevant tmLanguage file, which are then mapped to colors by the active colours 141 | theme. 142 | 143 | To see the actual scope at a cursor position: 144 | 145 | 1. Place your cursor on the word (e.g. TIME) 146 | 1. Press Ctrl+Shift+P (or Cmd+Shift+P on Mac) 147 | 1. Type and select: Developer: Inspect Editor Tokens and Scopes 148 | 1. This shows you the exact scope name and the colours applied by your theme 149 | -------------------------------------------------------------------------------- /dev/sql/keywords.txt: -------------------------------------------------------------------------------- 1 | ABSENT 2 | ACCORDING 3 | ACCTNG 4 | ACTION 5 | ACTIVATE 6 | ADD 7 | ALIAS 8 | ALL 9 | ALLOCATE 10 | ALLOW 11 | ALTER 12 | AND 13 | ANY 14 | APPEND 15 | APPLNAME 16 | ARRAY 17 | ARRAY_AGG 18 | AS 19 | ASC 20 | ASENSITIVE 21 | ASSOCIATE 22 | AT 23 | ATOMIC 24 | ATTRIBUTES 25 | AUTHORIZATION 26 | AUTONOMOUS 27 | BEFORE 28 | BEGIN 29 | BETWEEN 30 | BINARY 31 | BIND 32 | BIT 33 | BUFFERPOOL 34 | BY 35 | CACHE 36 | CALL 37 | CALLED 38 | CARDINALITY 39 | CASE 40 | CAST 41 | CCSID 42 | CHAR 43 | CHARACTER 44 | CHECK 45 | CL 46 | CLOSE 47 | CLUSTER 48 | COLLECT 49 | COLLECTION 50 | COLUMN 51 | COMMENT 52 | COMMIT 53 | COMPACT 54 | COMPRESS 55 | CONCAT 56 | CONCURRENT 57 | CONDITION 58 | CONNECT 59 | CONNECT_BY_ROOT 60 | CONNECTION 61 | CONSTANT 62 | CONSTRAINT 63 | CONTAINS 64 | CONTENT 65 | CONTINUE 66 | COPY 67 | COUNT 68 | COUNT_BIG 69 | CREATE 70 | CREATEIN 71 | CROSS 72 | CUBE 73 | CURRENT 74 | CURRENT_DATE 75 | CURRENT_PATH 76 | CURRENT_SCHEMA 77 | CURRENT_SERVER 78 | CURRENT_TIME 79 | CURRENT_TIMESTAMP 80 | CURRENT_TIMEZONE 81 | CURRENT_USER 82 | CURSOR 83 | CYCLE 84 | DATA 85 | DATABASE 86 | DATAPARTITIONNAME 87 | DATAPARTITIONNUM 88 | DATE 89 | DAY 90 | DAYS 91 | DBINFO 92 | DBPARTITIONNAME 93 | DBPARTITIONNUM 94 | DB2GENERAL 95 | DB2GENRL 96 | DB2SQL 97 | DEACTIVATE 98 | DEALLOCATE 99 | DECLARE 100 | DEFAULT 101 | DEFAULTS 102 | DEFER 103 | DEFINE 104 | DEFINITION 105 | DELETE 106 | DELETING 107 | DENSERANK 108 | DENSE_RANK 109 | DESC 110 | DESCRIBE 111 | DESCRIPTOR 112 | DETERMINISTIC 113 | DIAGNOSTICS 114 | DISABLE 115 | DISALLOW 116 | DISCONNECT 117 | DISTINCT 118 | DO 119 | DOCUMENT 120 | DOUBLE 121 | DROP 122 | DYNAMIC 123 | EACH 124 | ELSE 125 | ELSEIF 126 | EMPTY 127 | ENABLE 128 | ENCODING 129 | ENCRYPTION 130 | END 131 | ENDING 132 | END-EXEC 133 | ENFORCED 134 | ERROR 135 | ESCAPE 136 | EVERY 137 | EXCEPT 138 | EXCEPTION 139 | EXCLUDING 140 | EXCLUSIVE 141 | EXECUTE 142 | EXISTS 143 | EXIT 144 | EXTEND 145 | EXTERNAL 146 | EXTRACT 147 | FENCED 148 | FETCH 149 | FIELDPROC 150 | FILE 151 | FINAL 152 | FOR 153 | FOREIGN 154 | FORMAT 155 | FREE 156 | FREEPAGE 157 | FROM 158 | FULL 159 | FUNCTION 160 | GBPCACHE 161 | GENERAL 162 | GENERATED 163 | GET 164 | GLOBAL 165 | GO 166 | GOTO 167 | GRANT 168 | GRAPHIC 169 | GROUP 170 | HANDLER 171 | HASH 172 | HASHED_VALUE 173 | HAVING 174 | HINT 175 | HOLD 176 | HOUR 177 | HOURS 178 | ID 179 | IDENTITY 180 | IF 181 | IGNORE 182 | IMMEDIATE 183 | IMPLICITLY 184 | IN 185 | INCLUDE 186 | INCLUDING 187 | INCLUSIVE 188 | INCREMENT 189 | INDEX 190 | INDEXBP 191 | INDICATOR 192 | INF 193 | INFINITY 194 | INHERIT 195 | INLINE 196 | INNER 197 | INOUT 198 | INSENSITIVE 199 | INSERT 200 | INSERTING 201 | INTEGRITY 202 | INTERSECT 203 | INTO 204 | IS 205 | ISOLATION 206 | ITERATE 207 | JAVA 208 | JOIN 209 | JSON_ARRAY 210 | JSON_ARRAYAGG 211 | JSON_EXISTS 212 | JSON_OBJECT 213 | JSON_OBJECTAGG 214 | JSON_QUERY 215 | JSON_TABLE 216 | JSON_VALUE 217 | KEEP 218 | KEY 219 | LABEL 220 | LANGUAGE 221 | LATERAL 222 | LEAVE 223 | LEFT 224 | LEVEL2 225 | LIKE 226 | LIMIT 227 | LINKTYPE 228 | LISTAGG 229 | LOCAL 230 | LOCALDATE 231 | LOCALTIME 232 | LOCALTIMESTAMP 233 | LOCATION 234 | LOCATOR 235 | LOCK 236 | LOCKSIZE 237 | LOG 238 | LOGGED 239 | LONG 240 | LOOP 241 | MAINTAINED 242 | MASK 243 | MATCHED 244 | MATERIALIZED 245 | MAXVALUE 246 | MERGE 247 | MICROSECOND 248 | MICROSECONDS 249 | MINPCTUSED 250 | MINUTE 251 | MINUTES 252 | MINVALUE 253 | MIXED 254 | MODE 255 | MODIFIES 256 | MONTH 257 | MONTHS 258 | NAMESPACE 259 | NAN 260 | NATIONAL 261 | NCHAR 262 | NCLOB 263 | NESTED 264 | NEW 265 | NEW_TABLE 266 | NEXTVAL 267 | NO 268 | NOCACHE 269 | NOCYCLE 270 | NODENAME 271 | NODENUMBER 272 | NOMAXVALUE 273 | NOMINVALUE 274 | NONE 275 | NOORDER 276 | NORMALIZED 277 | NOT 278 | NULL 279 | NULLS 280 | NVARCHAR 281 | OBID 282 | OF 283 | OFFSET 284 | OLD 285 | OLD_TABLE 286 | OMIT 287 | ON 288 | ONLY 289 | OPEN 290 | OPTIMIZE 291 | OPTION 292 | OR 293 | ORDER 294 | ORDINALITY 295 | ORGANIZE 296 | OUT 297 | OUTER 298 | OVER 299 | OVERLAY 300 | OVERRIDING 301 | PACKAGE 302 | PADDED 303 | PAGE 304 | PAGESIZE 305 | PARAMETER 306 | PART 307 | PARTITION 308 | PARTITIONED 309 | PARTITIONING 310 | PARTITIONS 311 | PASSING 312 | PASSWORD 313 | PATH 314 | PCTFREE 315 | PERMISSION 316 | PIECESIZE 317 | PIPE 318 | PLAN 319 | POSITION 320 | PREPARE 321 | PREVVAL 322 | PRIMARY 323 | PRIOR 324 | PRIQTY 325 | PRIVILEGES 326 | PROCEDURE 327 | PROGRAM 328 | PROGRAMID 329 | QUERY 330 | RANGE 331 | RANK 332 | RCDFMT 333 | READ 334 | READS 335 | RECOVERY 336 | REFERENCES 337 | REFERENCING 338 | REFRESH 339 | REGEXP_LIKE 340 | RELEASE 341 | RENAME 342 | REPEAT 343 | RESET 344 | RESIGNAL 345 | RESTART 346 | RESULT 347 | RESULT_SET_LOCATOR 348 | RETURN 349 | RETURNING 350 | RETURNS 351 | REVOKE 352 | RID 353 | RIGHT 354 | ROLLBACK 355 | ROLLUP 356 | ROUTINE 357 | ROW 358 | ROWNUMBER 359 | ROW_NUMBER 360 | ROWS 361 | RRN 362 | RUN 363 | SAVEPOINT 364 | SBCS 365 | SCHEMA 366 | SCRATCHPAD 367 | SCROLL 368 | SEARCH 369 | SECOND 370 | SECONDS 371 | SECQTY 372 | SECURED 373 | SELECT 374 | SENSITIVE 375 | SEQUENCE 376 | SESSION 377 | SESSION_USER 378 | SET 379 | SIGNAL 380 | SIMPLE 381 | SKIP 382 | SNAN 383 | SOME 384 | SOURCE 385 | SPECIFIC 386 | SQL 387 | SQLID 388 | STACKED 389 | START 390 | STARTING 391 | STATEMENT 392 | STATIC 393 | STOGROUP 394 | SUBSTRING 395 | SUMMARY 396 | SYNONYM 397 | SYSTEM_USER 398 | TABLE 399 | TABLESPACE 400 | TABLESPACES 401 | THEN 402 | THREADSAFE 403 | TIME 404 | TIMESTAMP 405 | TO 406 | TRANSACTION 407 | TRANSFER 408 | TRIGGER 409 | TRIM 410 | TRIM_ARRAY 411 | TRUNCATE 412 | TYPE 413 | UNDO 414 | UNION 415 | UNIQUE 416 | UNIT 417 | UNNEST 418 | UNTIL 419 | UPDATE 420 | UPDATING 421 | URI 422 | USAGE 423 | USE 424 | USER 425 | USERID 426 | USING 427 | VALUE 428 | VALUES 429 | VARIABLE 430 | VARIANT 431 | VCAT 432 | VERSION 433 | VIEW 434 | VOLATILE 435 | WAIT 436 | WHEN 437 | WHENEVER 438 | WHERE 439 | WHILE 440 | WITH 441 | WITHIN 442 | WITHOUT 443 | WRAPPED 444 | WRAPPER 445 | WRITE 446 | WRKSTNNAME 447 | XMLAGG 448 | XMLATTRIBUTES 449 | XMLCAST 450 | XMLCOMMENT 451 | XMLCONCAT 452 | XMLDOCUMENT 453 | XMLELEMENT 454 | XMLFOREST 455 | XMLGROUP 456 | XMLNAMESPACES 457 | XMLPARSE 458 | XMLPI 459 | XMLROW 460 | XMLSERIALIZE 461 | XMLTABLE 462 | XMLTEXT 463 | XMLVALIDATE 464 | XSLTRANSFORM 465 | XSROBJECT 466 | YEAR 467 | YEARS 468 | YES 469 | ZONE -------------------------------------------------------------------------------- /tests/general/test3.mi: -------------------------------------------------------------------------------- 1 | /********************************************************************/ 2 | /* */ 3 | /* program Name: MICRTPG2 */ 4 | /* */ 5 | /* programming Language: MI */ 6 | /* */ 7 | /* Description: Initial version of MI program MICRTPG2, */ 8 | /* which calls QPRCRTPG API. */ 9 | /* */ 10 | /* From: https://www.ibm.com/support/ */ 11 | /* knowledgecenter/ssw_ibm_i_73/rzatk/MIcodeex.htm */ 12 | /* */ 13 | /********************************************************************/ 14 | /* Entry point and associated parameters */ 15 | 16 | ENTRY * (*ENTRY) EXT; 17 | DCL SPCPTR FIL@ PARM; 18 | DCL SPCPTR MBR@ PARM; 19 | DCL OL *ENTRY (MBR@, FIL@) PARM EXT MIN(1); 20 | DCL DD FIL CHAR(10) BAS(FIL@); 21 | DCL DD MBR CHAR(10) BAS(MBR@); 22 | DCL DD NUM_PARMS BIN( 4); 23 | 24 | /* Control field for first time initialization */ 25 | 26 | DCL DD READY CHAR( 1) INIT("0"); 27 | 28 | /* Binary offset into the space */ 29 | 30 | DCL DD BINOFFSET BIN(4) AUTO INIT(0); 31 | DCL SPCPTR BINOFFSET@ AUTO INIT(BINOFFSET); 32 | 33 | /* Pointers for accessing the space */ 34 | 35 | DCL SPCPTR USRSPC; 36 | DCL SYSPTR USRSPC@; 37 | 38 | /* QCMDEXC and associated CL commands */ 39 | 40 | DCL SYSPTR QCMDEXC INIT("QCMDEXC", CTX("QSYS"), TYPE(PGM)); 41 | DCL DD CLOVRCMD CHAR(65); 42 | DCL DD OVRSTR CHAR(39) DEF(CLOVRCMD) POS(1) 43 | INIT("OVRDBF MISRC 1234567890 MBR(1234567890)"); 44 | DCL DD OVRSTR2 CHAR(26) DEF(CLOVRCMD) POS(40) 45 | INIT(" POSITION(*RRN 1234567890)"); 46 | DCL DD FILNAM CHAR(10) DEF(CLOVRCMD) POS(14); 47 | DCL DD MBRNAM CHAR(10) DEF(CLOVRCMD) POS(29); 48 | DCL DD RECNUM ZND(10,0) DEF(CLOVRCMD) POS(55); 49 | DCL SPCPTR CLOVRCMD@ INIT(CLOVRCMD); 50 | DCL DD CLOVRLNG PKD(15,5) INIT(P'65'); 51 | DCL SPCPTR CLOVRLNG@ INIT(CLOVRLNG); 52 | DCL OL QCMDOVROL (CLOVRCMD@, CLOVRLNG@) ARG; 53 | DCL DD CLDLTCMD CHAR(12) INIT("DLTOVR MISRC"); 54 | DCL SPCPTR CLDLTCMD@ INIT(CLDLTCMD); 55 | DCL DD CLDLTLNG PKD(15,5) INIT(P'12'); 56 | DCL SPCPTR CLDLTLNG@ INIT(CLDLTLNG); 57 | DCL OL QCMDDLTOL (CLDLTCMD@, CLDLTLNG@) ARG; 58 | 59 | /* CL06 and associated parameters */ 60 | 61 | DCL SYSPTR CL06 INIT("CL06", TYPE(PGM)); 62 | DCL DD OFFSET PKD(15,5); 63 | DCL SPCPTR OFFSET@ INIT(OFFSET); 64 | DCL OL CL06OL (USRSPC, OFFSET@) ARG; 65 | 66 | /* Access QTEMP address */ 67 | 68 | DCL SYSPTR QTEMP@ BASPCO POS(65); 69 | 70 | /* Template for CRTS MI instruction */ 71 | 72 | DCL DD CRTSTMPLT CHAR(160) BDRY(16); 73 | DCL DD TMPLTSPEC CHAR(8) DEF(CRTSTMPLT) POS(1); 74 | DCL DD TMPLTSIZE BIN(4) DEF(TMPLTSPEC) POS(1) INIT(160); 75 | DCL DD TMPLTBA BIN(4) DEF(TMPLTSPEC) POS(5) INIT(0); 76 | DCL DD OBJID CHAR(32) DEF(CRTSTMPLT) POS(9); 77 | DCL DD SPCTYPE CHAR(1) DEF(OBJID) POS(1) INIT(X'19'); 78 | DCL DD SPCSUBTYPE CHAR(1) DEF(OBJID) POS(2) INIT(X'EF'); 79 | DCL DD SPCNAME CHAR(30) DEF(OBJID) POS(3) INIT("MICRTPG2"); 80 | DCL DD OBJCRTOPT CHAR(4) DEF(CRTSTMPLT) POS(41) INIT(X'60020000'); 81 | DCL DD OBJRCVOPTS CHAR(4) DEF(CRTSTMPLT) POS(45); 82 | DCL DD * CHAR(2) DEF(OBJRCVOPTS) POS(1) INIT(X'0000'); 83 | DCL DD ASP CHAR(2) DEF(OBJRCVOPTS) POS(3) INIT(X'0000'); 84 | DCL DD SPCSIZ BIN(4) DEF(CRTSTMPLT) POS(49) INIT(1); 85 | DCL DD INTSPCVAL CHAR(1) DEF(CRTSTMPLT) POS(53) INIT(X'00'); 86 | DCL DD PERFCLASS CHAR(4) DEF(CRTSTMPLT) POS(54) INIT(X'00000000'); 87 | DCL DD * CHAR(1) DEF(CRTSTMPLT) POS(58) INIT(X'00'); 88 | DCL DD PUBAUT CHAR(2) DEF(CRTSTMPLT) POS(59) INIT(X'0000'); 89 | DCL DD TMPLTEXTN BIN(4) DEF(CRTSTMPLT) POS(61) INIT(96); 90 | DCL SYSPTR CONTEXT DEF(CRTSTMPLT) POS(65); 91 | DCL SYSPTR ACCESSGRP DEF(CRTSTMPLT) POS(81); 92 | DCL SYSPTR USRPRF DEF(CRTSTMPLT) POS(97); 93 | DCL DD MAXSPCSIZ BIN(4) DEF(CRTSTMPLT) POS(113) INIT(0); 94 | DCL DD DOMAIN CHAR(2) DEF(CRTSTMPLT) POS(117) INIT(X'0001'); 95 | DCL DD * CHAR(42) DEF(CRTSTMPLT) POS(119) INIT((42)X'00'); 96 | DCL SPCPTR CRTSTMPLT@ INIT(CRTSTMPLT); 97 | 98 | /* QPRCRTPG and associated parameters */ 99 | 100 | DCL DD PGM CHAR(20); 101 | DCL DD PGMNAM CHAR(10) DEF(PGM) POS(1); 102 | DCL DD PGMLIBNAM CHAR(10) DEF(PGM) POS(11) INIT("*CURLIB "); 103 | DCL SPCPTR PGM@ INIT(PGM); 104 | DCL DD PGMTXT CHAR(50) INIT(" "); 105 | DCL SPCPTR PGMTXT@ INIT(PGMTXT); 106 | DCL DD PGMSRCF CHAR(20) INIT("*NONE"); 107 | DCL SPCPTR PGMSRCF@ INIT(PGMSRCF); 108 | DCL DD PGMSRCM CHAR(10) INIT(" "); 109 | DCL SPCPTR PGMSRCM@ INIT(PGMSRCM); 110 | DCL DD PGMSRCCHG CHAR(13) INIT(" "); 111 | DCL SPCPTR PGMSRCCHG@ INIT(PGMSRCCHG); 112 | DCL DD PRTFNAM CHAR(20) INIT("QSYSPRT *LIBL "); 113 | DCL SPCPTR PRTFNAM@ INIT(PRTFNAM); 114 | DCL DD PRTSTRPAG BIN(4) INIT(1); 115 | DCL SPCPTR PRTSTRPAG@ INIT(PRTSTRPAG); 116 | DCL DD PGMPUBAUT CHAR(10) INIT("*ALL "); 117 | DCL SPCPTR PGMPUBAUT@ INIT(PGMPUBAUT); 118 | DCL DD PGMOPTS(16) CHAR(11) INIT((1)"*LIST", *(2)(1)"*REPLACE", 119 | *(3)(1)"*XREF"); 120 | DCL SPCPTR PGMOPTS@ INIT(PGMOPTS); 121 | DCL DD NUMOPTS BIN(4) INIT(3); 122 | DCL SPCPTR NUMOPTS@ INIT(NUMOPTS); 123 | DCL OL QPRCRTPGOL (USRSPC, BINOFFSET@, PGM@, PGMTXT@, PGMSRCF@, 124 | PGMSRCM@, PGMSRCCHG@, PRTFNAM@, PRTSTRPAG@, 125 | PGMPUBAUT@, PGMOPTS@, NUMOPTS@) ARG; 126 | DCL SYSPTR QPRCRTPG INIT("QPRCRTPG", CTX("QSYS"), TYPE(PGM)); 127 | 128 | /* Start of instruction stream */ 129 | 130 | STPLLEN NUM_PARMS; 131 | CMPNV(B) NUM_PARMS, 2 / EQ(PARM2); 132 | CPYBLAP FILNAM, 'MISRC', ' '; 133 | B PARM1; 134 | PARM2: CPYBLA FILNAM, FIL; 135 | PARM1: CPYBLA MBRNAM,MBR; 136 | CMPBLA(B) READY, '1' / EQ(SKIP); 137 | CPYBWP CONTEXT, QTEMP@; 138 | CRTS USRSPC@, CRTSTMPLT@; 139 | SETSPPFP USRSPC,USRSPC@; 140 | CPYBLA READY, '1'; 141 | SKIP: CPYNV RECNUM, 1; 142 | MORE: CALLX QCMDEXC, QCMDOVROL, *; 143 | CPYNV OFFSET,1; 144 | CALLX CL06, CL06OL, *; 145 | SUBN(S) OFFSET, 1; 146 | ADDN(S) BINOFFSET, OFFSET; 147 | SETSPPO USRSPC, BINOFFSET; 148 | ADDN(S) RECNUM, 20; 149 | CALLX QCMDEXC, QCMDDLTOL, *; 150 | CMPNV(B) OFFSET, 1600 /EQ(MORE); 151 | CPYBLA PGMNAM, MBR; 152 | SETSPPO USRSPC, 0; 153 | CALLX QPRCRTPG, QPRCRTPGOL, *; 154 | RTX *; 155 | PEND; -------------------------------------------------------------------------------- /syntaxes/dds.dspf.tmLanguage.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", 3 | "name": "DDS.DSPF", 4 | "patterns": [ 5 | { 6 | "include": "#comments" 7 | }, 8 | { 9 | "include": "#constants" 10 | }, 11 | { 12 | "include": "#keywords" 13 | }, 14 | { 15 | "include": "#gutter" 16 | }, 17 | { 18 | "include": "#strings" 19 | } 20 | ], 21 | "repository": { 22 | "comments": { 23 | "patterns": [ 24 | { 25 | "name": "comment.line.dds.dspf", 26 | "match": "^.{5}(.)(\\*).*" 27 | } 28 | ] 29 | }, 30 | "gutter": { 31 | "patterns": [ 32 | { 33 | "name": "comment.gutter", 34 | "match": "^.{5}" 35 | } 36 | ] 37 | }, 38 | "constants": { 39 | "patterns": [ 40 | { 41 | "name": "constant.language.dds.dspf", 42 | "match": "(\\*)[a-zA-Z][a-zA-Z0-9]*" 43 | }, 44 | { 45 | "name": "constant.language.dds.dspf.andor", 46 | "match": "(?i)(?<=^.{5}(A|\\s).{0})(A|O)" 47 | }, 48 | { 49 | "name": "constant.language.dds.dspf.n01", 50 | "match": "(?i)(?<=^.{5}(A|\\s).{1})(N|\\s)[0-9]{2}" 51 | }, 52 | { 53 | "name": "constant.language.dds.dspf.n02", 54 | "match": "(?i)(?<=^.{5}(A|\\s).{4})(N|\\s)[0-9]{2}" 55 | }, 56 | { 57 | "name": "constant.language.dds.dspf.n03", 58 | "match": "(?i)(?<=^.{5}(A|\\s).{7})(N|\\s)[0-9]{2}" 59 | }, 60 | { 61 | "name": "constant.language.dds.dspf.nameType", 62 | "match": "(?i)(?<=^.{5}(A|\\s).{10})(R|H)" 63 | }, 64 | { 65 | "name": "constant.language.dds.dspf.ref", 66 | "match": "(?i)(?<=^.{5}(A|\\s).{22})(R)" 67 | }, 68 | { 69 | "name": "constant.language.dds.dspf.len", 70 | "match": "(?i)(?<=^.{5}(A|\\s).{23})[0-9|\\s]{5}" 71 | }, 72 | { 73 | "name": "constant.language.dds.dspf.dataType", 74 | "match": "(?i)(?<=^.{5}(A|\\s).{28})(A|D|E|F|G|I|J|L|M|N|O|S|T|W|X|Y|Z)" 75 | }, 76 | { 77 | "name": "constant.language.dds.dspf.decpos", 78 | "match": "(?i)(?<=^.{5}(A|\\s).{29})[0-9|\\s]{2}" 79 | }, 80 | { 81 | "name": "constant.language.dds.dspf.usage", 82 | "match": "(?i)(?<=^.{5}(A|\\s).{31})(O|I|B|H|M|P)" 83 | }, 84 | { 85 | "name": "constant.language.dds.dspf.locline", 86 | "match": "(?i)(?<=^.{5}(A|\\s).{32})([0-9]|\\s){3}" 87 | }, 88 | { 89 | "name": "constant.language.dds.dspf.locpos", 90 | "match": "(?i)(?<=^.{5}(A|\\s).{35})([0-9]|\\s){3}" 91 | }, 92 | { 93 | "name": "constant.numeric.dds.dspf", 94 | "match": "\\b([0-9]+)\\b" 95 | }, 96 | { 97 | "name": "dds.dspf.check", 98 | "begin": "(?i)(?<=(CHECK\\())", 99 | "end": "(?=(\\)))", 100 | "patterns": [ 101 | { 102 | "name": "constant.other.dds.dspf.check.values", 103 | "match": "(?i)(\\b(AB|ME|MF|M10F|M10|M11F|M11|VNE|VN|ER|FE|LC|RB|RZ|RLTB|RL)\\b)" 104 | } 105 | ] 106 | }, 107 | { 108 | "name": "dds.dspf.dspatr", 109 | "begin": "(?i)(?<=(DSPATR\\())", 110 | "end": "(?=(\\)))", 111 | "patterns": [ 112 | { 113 | "name": "constant.other.dds.dspf.dspatr.values", 114 | "match": "(?i)(\\b(SP|PR|OID|MDT|UL|RI|PC|ND|HI|CS|BL)\\b)" 115 | } 116 | ] 117 | }, 118 | { 119 | "name": "dds.dspf.color", 120 | "begin": "(?i)(?<=(COLOR\\())", 121 | "end": "(?=(\\)))", 122 | "patterns": [ 123 | { 124 | "name": "constant.other.dds.dspf.color.values", 125 | "match": "(?i)(\\b(BLU|PNK|YLW|TRQ|RED|WHT|GRN)\\b)" 126 | } 127 | ] 128 | }, 129 | { 130 | "name": "dds.dspf.comp", 131 | "begin": "(?i)((?<=((COMP)\\())|(?<=((CMP)\\()))", 132 | "end": "(?=(\\)))", 133 | "patterns": [ 134 | { 135 | "name": "keyword.other.dds.dspf.comp.values", 136 | "match": "(?i)(\\b(GE|LE|NG|GT|NL|LT|NE|EQ)\\b)" 137 | }, 138 | { 139 | "name": "constant.numeric.dds.dspf", 140 | "match": "\\b([0-9]+)\\b" 141 | } 142 | ] 143 | } 144 | ] 145 | }, 146 | "keywords": { 147 | "patterns": [ 148 | { 149 | "name": "keyword.other.dds.dspf.spec", 150 | "match": "(?i)(?<=^.{5})[A]" 151 | }, 152 | { 153 | "name": "keyword.other.dds.dspf", 154 | "match": "\\+" 155 | }, 156 | { 157 | "name": "keyword.other.dds.dspf.func", 158 | "match": "((?i)(C(A|F)))[0-9]{2}" 159 | }, 160 | { 161 | "name": "keyword.other.dds.dspf.funcs", 162 | "match": "(?i)(?<=(.{44}))(WRDWRAP|WINDOW|WDWTITLE|WDWBORDER|VLDCMDKEY|VALUES|VALNUM|USRRSTDSP|USRDSPMGT|USRDFN|USER|UNLOCK|TIMSEP|TIMFMT|TIME|TEXT|SYSNAME|SNGCHCFLD|SLNO|SFLSNGCHC|SFLSIZ|SFLSCROLL|SFLRTNSEL|SFLROLVAL|SFLRNA|SFLRCDNBR|SFLPGMQ|SFLPAG|SFLNXTCHG|SFLMSGRCD|SFLMSGKEY|SFLMSG|SFLMODE|SFLMLTCHC|SFLLIN|SFLINZ|SFLFOLD|SFLENTER|SFLEND|SFLDSPCTL|SFLDSP|SFLDROP|SFLDLT|SFLCTL|SFLCSRRRN|SFLCSRPRG|SFLCLR|SFLCHCCTL|SETOFF|SETOF|RTNDTA|RTNCSRLOC|ROLLUP|ROLLDOWN|RMVWDW|RETLCKSTS|RETKEY|REFFLD|REF|RANGE|PUTRETAIN|PUTOVR|PULLDOWN|PSHBTNFLD|PSHBTNCHC|PROTECT|PRINT|PASSRCD|PAGEDOWN|PAGEUP|OVRDTA|OVRATR|OVERLAY|OPENPRT|NOCCSID|MSGLOC|MSGID|MSGCON|MSGALARM|MOUBTN|MNUCNL|MNUBARSW|MNUBARSEP|MNUBARDSP|MNUBARCHC|MNUBAR|MLTCHCFLD|MDTOFF|MAPVAL|LOWER|LOGOUT|LOGINP|LOCK|KEEP|INZRCD|INZINP|INVITE|INDTXT|INDARA|HTML|HOME|HLPTITLE|HLPSEQ|HLPSCHIDX|HLPRTN|HLPRCD|HLPPNLGRP|HLPID|HLPFULL|HLPEXCLD|HLPDOC|HLPCMDKEY|HLPCLR|HLPBDY|HLPARA|HELP|GETRETAIN|FRCDTA|FLTPCN|FLTFIXDEC|FLDCSRPRG|ERRSFL|ERRMSG|ERRMSGID|ERASEINP|ERASE|ENTFLDATR|EDTWRD|EDTMSK|EDTCDE|DUP|DSPSIZ|DSPRL|DSPMOD|DSPATR|DLTEDT|DLTCHK|DFTVAL|DFT|DATSEP|DATFMT|DATE|CSRLOC|CSRINPONLY|COMP|COLOR|CNTFLD|CLEAR|CHRID|CHOICE|CHKMSGID|CHGINPDFT|CHECK|CHCUNAVAIL|CHCSLT|CHCCTL|CHCAVAIL|CHCACCEL|CHANGE|BLKFOLD|BLINK|BLANKS|AUTO|ASSUME|ALWROL|ALWGPH|ALTPAGEDWN|ALTPAGEUP|ALTNAME|ALTHELP|ALIAS|ALARM)\\b" 163 | }, 164 | { 165 | "name": "keyword.other.dds.dspf.funcs", 166 | "match": "\\b(?i)(CMP|CLRL|SFL)\\b" 167 | } 168 | ] 169 | }, 170 | "strings": { 171 | "name": "string.quoted.single.dds.dspf", 172 | "begin": "'", 173 | "end": "'", 174 | "patterns": [ 175 | { 176 | "name": "keyword.other.dds.dspf.spec", 177 | "match": "(?i)(?<=^.{5})[A]" 178 | } 179 | ] 180 | } 181 | }, 182 | "scopeName": "source.dds.dspf" 183 | } -------------------------------------------------------------------------------- /tests/general/test-fixed.rpgle: -------------------------------------------------------------------------------- 1 | H/TITLE Testing syntax highlighting 2 | * 3 | H* Test control spec 4 | H DATFMT(*YMD) DATEDIT(*YMD) DEBUG(*YES) OPTION(*NODEBUGIO) h spec comment 5 | * 6 | F* Test file spec (program described) 7 | FSOMEFILE OTEAAF12345L12345ZIWORKSTN EXTDESC(FILE123) f spec comment 8 | * 9 | F* Test file spec (externally described) 10 | FANOTHRFILEUPEADE L G SPECIAL INDDS(SOMEDS) f spec comment 11 | 12 | * Test USROPN keyword 13 | FBADFILE IF F 100 DISK USROPN 14 | 15 | * 16 | I* Test input spec 17 | IMYFILE A1NO**11111NCX22222NZY33333NDZ i spec comment 18 | * 19 | D* Test definition spec 20 | DMYFIELD ESS *OPCODE-12345 *12 NOOPT d spec comment 21 | D MSG S 52A 22 | D FieldA S 10A INZ('Value of A') 23 | D FieldB S 10A INZ('Value of B') 24 | D FieldC S 10A INZ('Value of C') 25 | * 26 | D* Test definition extended (DX) spec 27 | D STREAM_NEW_LINE... dx spec comment 28 | * 29 | C* Test calculation spec 30 | CSRNH4FACTOR1 ADD FACTOR2 RESULT 1234533KCU7OV c spec comment 31 | * 32 | CL4 KPMYFIELD IF ANOTHERFIELD = 'something' c spec comment 33 | * 34 | C/COPY /something 35 | * 36 | O* Test ouput spec 37 | OMYFILE TF N02 OGN1PSOMERECRDS123222100105 o spec comment 38 | * 39 | P* Test procedure spec 40 | PMYPROC B EXPORT p spec - begin procedure 41 | PMYPROC E p spec - end procedure 42 | * 43 | /EJECT 44 | 45 | * Test /TITLE for all line line types 46 | 47 | H/title title text 48 | F/title title text 49 | I/title title text 50 | D/title title text 51 | C/title title text 52 | O/title title text 53 | P/title title text 54 | /title title text 55 | 56 | * Test /EJECT for all line line types 57 | 58 | H/eject 59 | F/eject 60 | I/eject 61 | D/eject 62 | C/eject 63 | O/eject 64 | P/eject 65 | /eject 66 | 67 | * Test /IF and /ENDIF 68 | 69 | H/if defined something 70 | H DECFMT('J') 71 | H/endif 72 | 73 | * Test /COPY and /INCLUDE 74 | 75 | H/copy lib/file.member 76 | H/include lib/file.member 77 | 78 | * Issue #76 79 | * - handle hyphenated opcodes and fields containing opcode words 80 | 81 | D end1 S 10i 0 82 | D endif_b S 10i 0 83 | D c_endif S 10i 0 84 | D endx S 10i 0 85 | D end#1 S 10i 0 86 | D end@1 S 10i 0 87 | D end$1 S 10i 0 88 | D end£1 S 10i 0 89 | D end§1 S 10i 0 90 | D #end1 S 10i 0 91 | D @end1 S 10i 0 92 | D $end1 S 10i 0 93 | D £end1 S 10i 0 94 | D §end1 S 10i 0 95 | 96 | C monitor Valid 97 | C on-error Valid 98 | C endmon Valid 99 | C end-mon Invalid 100 | C end-monitor Invalid 101 | C abc-monitor Invalid 102 | 103 | C Eval end1 = 1 104 | C Eval endif_b = 2 105 | C Eval c_endif = 3 106 | C Eval endx = 4 107 | C Eval end#1 = 5 108 | C Eval end@1 = 6 109 | C Eval end$1 = 7 110 | C Eval end£1 = 8 111 | C Eval end§1 = 9 112 | C Eval #end1 = 5 113 | C Eval @end1 = 6 114 | C Eval $end1 = 7 115 | C Eval £end1 = 8 116 | C Eval §end1 = 9 117 | 118 | C endif Valid 119 | C endif-abc Invalid 120 | C endif-test Invalid 121 | 122 | C acq valid 123 | C acq-test Invalid 124 | C acquire Invalid 125 | 126 | C CUSCOD Chain(N) CUSTOMERS 21 127 | C CUSCOD Chain(EN) CUSTOMERS 21 128 | 129 | 130 | * Test DO group 131 | C DO 10 X 3 0 132 | C SND-MSG 'X='+%CHAR(X) 133 | C ENDDO 134 | 135 | * Test CASxx group 136 | C FieldA CASGE FieldB Subr01 137 | C FieldA CASEQ FieldC Subr02 138 | C CAS Subr03 139 | C ENDCS 140 | 141 | * Test IF group 142 | C IF X = 10 143 | C SND-MSG 'X is now equal to 10' 144 | C ELSE 145 | C IF X < 10 146 | C SND-MSG 'X is now less than 10' 147 | C ELSEIF X > 10 148 | C SND-MSG 'X is now greater than 10' 149 | C ELSE 150 | C SND-MSG 'X is now equal to '+%CHAR(X) 151 | C END 152 | C ENDIF 153 | 154 | * Test FOR group 155 | C FOR X = 1 TO 10 156 | C EVAL X = X + X 157 | C ENDFOR 158 | 159 | * Test MONITOR GROUP plus SND-MSG and ON-EXCP opcodes 160 | 161 | C MONITOR 162 | C OPEN BADFILE 163 | C EVAL MSG = 'BADFILE opened' 164 | C ON-EXCP 'CPF4101' 165 | C EVAL MSG = 'Message CPF4101: ' + %CHAR(%STATUS()) 166 | C ON-EXCP 'RNX1217' 167 | C EVAL MSG = 'Message RNX1217' 168 | C ON-ERROR 1217 169 | C EVAL MSG = 'Status 1217' 170 | C ENDMON 171 | C SND-MSG MSG 172 | 173 | * Test SELECT group 174 | C SELECT 175 | C WHEN X = 1 176 | C Eval FieldA = 'aaa' 177 | C WHEN X = 2 178 | C Eval FieldB = 'bbb' 179 | C WHEN X = 3 180 | C Eval FieldC = 'ccc' 181 | C OTHER 182 | C Eval FieldA = 'xxx' 183 | C Eval FieldB = 'xxx' 184 | C Eval FieldC = 'xxx' 185 | C ENDSL 186 | 187 | C SETON LR 188 | 189 | C Subr01 BEGSR 190 | C SND-MSG FieldA+'>='+FieldB 191 | C ENDSR 192 | 193 | C Subr02 BEGSR 194 | C SND-MSG FieldA+'>='+FieldC 195 | C ENDSR 196 | 197 | C Subr03 BEGSR 198 | C SND-MSG FieldA+'<'+FieldB+' and <'+FieldC 199 | C ENDSR 200 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "ibmi-languages", 3 | "displayName": "IBMi Languages", 4 | "description": "Syntax highlighting for IBM i languages such as RPG, CL, DDS, MI, and RPGLE fixed/free.", 5 | "version": "0.6.24", 6 | "publisher": "barrettotte", 7 | "author": { 8 | "name": "Barrett Otte" 9 | }, 10 | "engines": { 11 | "vscode": "^1.38.0" 12 | }, 13 | "categories": [ 14 | "Programming Languages" 15 | ], 16 | "contributes": { 17 | "languages": [ 18 | { 19 | "id": "bnd", 20 | "aliases": [ 21 | "BND", 22 | "Binder Language" 23 | ], 24 | "extensions": [ 25 | ".bnd" 26 | ], 27 | "configuration": "./configurations/bnd.language-configuration.json" 28 | }, 29 | { 30 | "id": "cl", 31 | "aliases": [ 32 | "CL", 33 | "CLLE", 34 | "CLP", 35 | "CLP38", 36 | "Control Language" 37 | ], 38 | "extensions": [ 39 | ".cl", 40 | ".clle", 41 | ".clp", 42 | ".clp38" 43 | ], 44 | "configuration": "./configurations/cl.language-configuration.json" 45 | }, 46 | { 47 | "id": "cmd", 48 | "aliases": [ 49 | "CMD", 50 | "Command Definition" 51 | ], 52 | "extensions": [ 53 | ".cmd" 54 | ], 55 | "configuration": "./configurations/cmd.language-configuration.json" 56 | }, 57 | { 58 | "id": "dds.dspf", 59 | "aliases": [ 60 | "DSPF" 61 | ], 62 | "extensions": [ 63 | ".dspf", 64 | ".dspf38" 65 | ], 66 | "configuration": "./configurations/dds.language-configuration.json" 67 | }, 68 | { 69 | "id": "dds.icff", 70 | "aliases": [ 71 | "ICFF" 72 | ], 73 | "extensions": [ 74 | ".icff" 75 | ], 76 | "configuration": "./configurations/dds.language-configuration.json" 77 | }, 78 | { 79 | "id": "dds.lf", 80 | "aliases": [ 81 | "LF" 82 | ], 83 | "extensions": [ 84 | ".lf", 85 | ".lf38" 86 | ], 87 | "configuration": "./configurations/dds.language-configuration.json" 88 | }, 89 | { 90 | "id": "dds.pf", 91 | "aliases": [ 92 | "DDS", 93 | "PF" 94 | ], 95 | "extensions": [ 96 | ".dds", 97 | ".pf", 98 | ".pf38" 99 | ], 100 | "configuration": "./configurations/dds.language-configuration.json" 101 | }, 102 | { 103 | "id": "dds.prtf", 104 | "aliases": [ 105 | "PRTF" 106 | ], 107 | "extensions": [ 108 | ".prtf", 109 | ".prtf38" 110 | ], 111 | "configuration": "./configurations/dds.language-configuration.json" 112 | }, 113 | { 114 | "id": "mi", 115 | "aliases": [ 116 | "MI" 117 | ], 118 | "extensions": [ 119 | ".MI" 120 | ], 121 | "configuration": "./configurations/mi.language-configuration.json" 122 | }, 123 | { 124 | "id": "pnlgrp", 125 | "aliases": [ 126 | "PNLGRP", 127 | "IBM UIM Panel Group Definition Language" 128 | ], 129 | "extensions": [ 130 | ".pnlgrp" 131 | ], 132 | "configuration": "./configurations/pnlgrp.language-configuration.json" 133 | }, 134 | { 135 | "id": "rpg", 136 | "aliases": [ 137 | "RPG", 138 | "SQLRPG", 139 | "RPG/400", 140 | "RPG38" 141 | ], 142 | "extensions": [ 143 | ".rpg", 144 | ".rpg38", 145 | ".sqlrpg" 146 | ], 147 | "configuration": "./configurations/rpg.language-configuration.json" 148 | }, 149 | { 150 | "id": "rpgle", 151 | "aliases": [ 152 | "RPGLE", 153 | "SQLRPGLE", 154 | "RPGLEINC" 155 | ], 156 | "extensions": [ 157 | ".rpgle", 158 | ".sqlrpgle", 159 | ".rpgleinc" 160 | ], 161 | "configuration": "./configurations/rpgle.language-configuration.json" 162 | } 163 | ], 164 | "grammars": [ 165 | { 166 | "language": "bnd", 167 | "scopeName": "source.bnd", 168 | "path": "./syntaxes/bnd.tmLanguage.json" 169 | }, 170 | { 171 | "language": "cl", 172 | "scopeName": "source.cl", 173 | "path": "./syntaxes/cl.tmLanguage.json" 174 | }, 175 | { 176 | "language": "cmd", 177 | "scopeName": "source.cmd", 178 | "path": "./syntaxes/cmd.tmLanguage.json" 179 | }, 180 | { 181 | "language": "dds.dspf", 182 | "scopeName": "source.dds.dspf", 183 | "path": "./syntaxes/dds.dspf.tmLanguage.json" 184 | }, 185 | { 186 | "language": "dds.icff", 187 | "scopeName": "source.dds.icff", 188 | "path": "./syntaxes/dds.icff.tmLanguage.json" 189 | }, 190 | { 191 | "language": "dds.lf", 192 | "scopeName": "source.dds.lf", 193 | "path": "./syntaxes/dds.lf.tmLanguage.json" 194 | }, 195 | { 196 | "language": "dds.pf", 197 | "scopeName": "source.dds.pf", 198 | "path": "./syntaxes/dds.pf.tmLanguage.json" 199 | }, 200 | { 201 | "language": "dds.prtf", 202 | "scopeName": "source.dds.prtf", 203 | "path": "./syntaxes/dds.prtf.tmLanguage.json" 204 | }, 205 | { 206 | "language": "mi", 207 | "scopeName": "source.mi", 208 | "path": "./syntaxes/mi.tmLanguage.json" 209 | }, 210 | { 211 | "language": "pnlgrp", 212 | "scopeName": "source.pnlgrp", 213 | "path": "./syntaxes/pnlgrp.tmLanguage.json" 214 | }, 215 | { 216 | "language": "rpg", 217 | "scopeName": "source.rpg", 218 | "path": "./syntaxes/rpg.tmLanguage.json" 219 | }, 220 | { 221 | "language": "rpgle", 222 | "scopeName": "source.rpgle", 223 | "path": "./syntaxes/rpgle.tmLanguage.json" 224 | } 225 | ] 226 | }, 227 | "icon": "images/icon.png", 228 | "devDependencies": { 229 | "js-yaml": "^3.13.1", 230 | "semver": "^7.3.5" 231 | }, 232 | "keywords": [ 233 | "RPG", 234 | "RPGLE", 235 | "IBMi", 236 | "AS/400", 237 | "SQLRPG", 238 | "SQLRPGLE", 239 | "CL", 240 | "CONTROL LANGUAGE", 241 | "DDS", 242 | "DSPF", 243 | "MI", 244 | "MACHINE INTERFACE", 245 | "ISERIES", 246 | "BINDER LANGUAGE" 247 | ], 248 | "license": "MIT", 249 | "repository": { 250 | "type": "git", 251 | "url": "https://github.com/barrettotte/vscode-ibmi-languages" 252 | } 253 | } 254 | -------------------------------------------------------------------------------- /tests/general/test-fullfree.rpgle: -------------------------------------------------------------------------------- 1 | **free 2 | 3 | // Testing fully free RPGLE 4 | 5 | // Test operators, literals, and constants 6 | x = 2 1 + 2 1 - 2 1 * 2 1 / 2 1 ** 2 7 | x += 1 x -= 1 x *= 1 x /= 1 x **= 2 8 | x > 1 x < 1 x = 1 x <> 1 x <= 1 x >= 1 9 | x=1 and y=1 x=1 or y=1 not x 10 | . , : 2.5 x'AF' 'a string' *ON *OFF *INLR=*ON; 11 | 12 | /FREE 13 | // Test control specifications 14 | ctl-opt; 15 | 16 | ctl-opt main(main); //inline comment 17 | /END-FREE 18 | 19 | H* Test control spec 20 | H DATFMT(*YMD) DATEDIT(*YMD) DEBUG(*YES) OPTION(*NODEBUGIO) h spec comment 21 | 22 | ctl-opt option(*srcstmt:*noDebugIO:*nounref) dftActGrp(*no); 23 | 24 | ctl-opt datfmt(*iso) timfmt(*iso) 25 | alwnull(*usrctl); 26 | 27 | ctl-opt option(*srcstmt)ccsid(*char:*jobrun); 28 | 29 | H OPTION(*SRCSTMT : 30 | H *NODEBUGIO) 31 | H ACTGRP(*NEW) 32 | CTL-OPT ALWNULL(*USRCTL) 33 | CCSID(*UCS2 34 | :1200) 35 | CCSID(*CHAR:*JOBRUN); 36 | H DATFMT(*YMD) TIMFMT(*USA) 37 | 38 | 39 | /FREE 40 | // Test file specifications 41 | DCL-F file1a; 42 | DCL-F file1b DISK(*EXT) USAGE(*INPUT); 43 | DCL-F file2 PRINTER; 44 | /END-FREE 45 | 46 | F* Test file spec (externally described) 47 | FANOTHRFILEUPEADE L G SPECIAL INDDS(SOMEDS) f spec comment 48 | 49 | DCL-F file3 SEQ; //inline comment 50 | DCL-F file4 WORKSTN; 51 | DCL-F file5 USAGE(*UPDATE) KEYED; 52 | 53 | F* Test file spec (externally described) 54 | FANOTHRFILEUPEADE L G SPECIAL INDDS(SOMEDS) f spec comment 55 | 56 | dcl-f CLS019B workstn indDs(dspf) usropn; 57 | 58 | 59 | 60 | // Test named constant definition 61 | DCL-C CON_1 CONST(1); //inline comment 62 | DCL-C CON_2 2; 63 | 64 | DCL-C array_total_size 65 | %SIZE(array:*ALL); 66 | 67 | 68 | // Test standalone field definition 69 | DCL-S limit PACKED(5) INZ(100); //inline comment 70 | 71 | D* Test definition spec 72 | DMYFIELD ESS *OPCODE-12345 *12 NOOPT d spec comment 73 | 74 | DCL-S num INZ(0) LIKE(limit); 75 | 76 | 77 | // Test data structure definition 78 | /FREE 79 | dcl-ds resp likeds(geoResponse); 80 | 81 | DCL-DS address; 82 | num int(5); 83 | street VARCHAR(25); 84 | city VARCHAR(25); 85 | province VARCHAR(25); 86 | postcode VARCHAR(6); 87 | END-DS address; 88 | 89 | DCL-DS person QUALIFIED; 90 | name VARCHAR(25); 91 | DCL-DS address; 92 | num int(5); 93 | street VARCHAR(25); 94 | city VARCHAR(25); 95 | province VARCHAR(25); 96 | postcode VARCHAR(6); 97 | END-DS address; 98 | age int(5); 99 | END-DS person; 100 | 101 | DCL-DS family QUALIFIED; 102 | num int(5); 103 | DCL-DS person DIM(10); 104 | name VARCHAR(25); 105 | age int(5); 106 | numPets int(5); 107 | DCL-DS pets DIM(5); 108 | name VARCHAR(25); 109 | type VARCHAR(25); 110 | END-DS pets; 111 | END-DS person; 112 | END-DS; 113 | 114 | 115 | // Test prototypes and procedure interfaces 116 | DCL-PI *N EXTPGM; 117 | name CHAR(10) CONST; 118 | END-PI; 119 | 120 | DCL-PI *N; 121 | id INT(10) VALUE; 122 | quantity INT(10) CONST; 123 | price PACKED(7:2) CONST; 124 | END-PI; 125 | 126 | DCL-PI *N CHAR(10) END-PI; //inline comment 127 | 128 | DCL-PI *N; 129 | DCL-PARM select CHAR(10); 130 | name CHAR(10); 131 | DCL-PARM address CHAR(25); 132 | END-PI; 133 | 134 | DCL-PR myPgm EXTPGM; //inline comment 135 | name CHAR(10) CONST; 136 | END-PR; 137 | 138 | DCL-PR addNewOrder; 139 | id INT(10) CONST; 140 | quantity INT(10) CONST; 141 | price PACKED(7:2) CONST; 142 | END-PR; 143 | 144 | DCL-PR getCurrentUser CHAR(10) END-PR; 145 | 146 | DCL-PR myProc; 147 | DCL-PARM select CHAR(10); 148 | name CHAR(10); 149 | DCL-PARM address CHAR(25); //inline comment 150 | END-PR; 151 | 152 | 153 | // Testing general 154 | read file; // Get next record 155 | dow not %eof(file); // Keep looping while we have 156 | // a record 157 | if %error; 158 | dsply 'The read failed'; 159 | leave; 160 | else; 161 | chain(n) name database data; 162 | time = hours * num_employees 163 | + overtime_saved; 164 | pos = %scan (',': name); 165 | name = %xlate(upper:lower:name); 166 | exsr handle_record; 167 | read file; 168 | endif; 169 | enddo; 170 | 171 | begsr handle_record; 172 | eval(h) time = time + total_hours_array (empno); 173 | temp_hours = total_hours - excess_hours; 174 | record_transaction(); 175 | endsr; 176 | 177 | 178 | DCL-S name 179 | /IF DEFINED(TRUE) 180 | CHAR(10); 181 | /ELSEIF DEFINED(TRUE OR FALSE) 182 | VARCHAR(10); 183 | /ELSE 184 | CHAR(12); 185 | /ENDIF 186 | 187 | /COPY /something 188 | /INCLUDE /something/else 189 | 190 | 191 | /copy mpkcorsrc,pr_f3gtrtd // comment 192 | dcl-s RLBERRCNT packed(3); // issue #19 193 | dcl-s i like(RLBERRCNT); 194 | 195 | /charcount STDCHARSIZE 196 | 197 | for x = 1 to 10 by 5; 198 | endfor; 199 | 200 | for y in %list( 'a' : 'b' : 'c'); 201 | endfor; 202 | 203 | if (a < b) and (c > d); 204 | endif; 205 | 206 | // Fall 2024 RPGLE enhancements: 207 | 208 | // New BIF's 209 | max = %hival( i ); 210 | min = %loval( i ); 211 | 212 | // New CTL-OPT keyword DATEYY 213 | ctl-opt dateyy(*warn); 214 | 215 | 216 | // Issue #76 217 | // - handle hyphenated opcodes and fields containing opcode words 218 | 219 | dcl-s end1 int(10); 220 | dcl-s endif_b int(10); 221 | dcl-s c_endif int(10); 222 | dcl-s endx int(10); 223 | dcl-s end#1 int(10); 224 | dcl-s end@1 int(10); 225 | dcl-s end$1 int(10); 226 | dcl-s end£1 int(10); 227 | dcl-s end§1 int(10); 228 | dcl-s #end1 int(10); 229 | dcl-s @end1 int(10); 230 | dcl-s $end1 int(10); 231 | dcl-s £end1 int(10); 232 | dcl-s §end1 int(10); 233 | 234 | monitor; // Valid 235 | on-error; // Valid 236 | endmon; // Valid 237 | end-mon; // Invalid 238 | end-monitor; // Invalid 239 | abc-monitor; // Invalid 240 | 241 | end1 = 1; 242 | endif_b = 2; 243 | c_endif = 3; 244 | endx = 4; 245 | end#1 = 5; 246 | end@1 = 6; 247 | end$1 = 7; 248 | end£1 = 8; 249 | end§1 = 9; 250 | #end1 = 5; 251 | @end1 = 6; 252 | $end1 = 7; 253 | £end1 = 8; 254 | §end1 = 9; 255 | 256 | endif; // Valid 257 | endif-abc; // Invalid 258 | endif-test; // Invalid 259 | 260 | acq; // Valid 261 | acq-test; // Invalid 262 | acquire; // Invalid 263 | 264 | Chain(N) CUSCOD CUSTOMERS; 265 | Chain(EN) CUSCOD CUSTOMERS; 266 | 267 | 268 | // PR #162 269 | // - all valid free format opcodes 270 | ACQ; 271 | ALLOC; 272 | BEGSR; 273 | CALLP; 274 | CHAIN; 275 | CLEAR; 276 | CLOSE; 277 | COMMIT; 278 | DATA-GEN; 279 | DATA-INTO; 280 | DEALLOC; 281 | DELETE; 282 | DOU; 283 | DOW; 284 | DSPLY; 285 | DUMP; 286 | ELSE; 287 | ELSEIF; 288 | ENDDO; 289 | ENDFOR; 290 | ENDIF; 291 | ENDMON; 292 | ENDSL; 293 | ENDSR; 294 | EVAL; 295 | EVALR; 296 | EVAL-CORR; 297 | EXCEPT; 298 | EXFMT; 299 | EXSR; 300 | FEOD; 301 | FOR; 302 | FOR-EACH; 303 | FORCE; 304 | IF; 305 | IN; 306 | ITER; 307 | LEAVE; 308 | LEAVESR; 309 | MONITOR; 310 | NEXT; 311 | ON-ERROR; 312 | ON-EXCP; 313 | ON-EXIT; 314 | OPEN; 315 | OTHER; 316 | OUT; 317 | POST; 318 | READ; 319 | READC; 320 | READE; 321 | READP; 322 | READPE; 323 | REL; 324 | RESET; 325 | RETURN; 326 | ROLBK; 327 | SELECT; 328 | SETGT; 329 | SETLL; 330 | SHTDN; 331 | SND-MSG; 332 | SORTA; 333 | TEST; 334 | UNLOCK; 335 | UPDATE; 336 | WHEN; 337 | WHEN-IN; 338 | WHEN-IS; 339 | WRITE; 340 | XML-INTO; 341 | XML-SAX; 342 | 343 | // - all fixed format opcodes that are not valid in free format 344 | ADD; 345 | ADDDUR; 346 | ACQUIRE; 347 | ANDEQ; 348 | ANDGE; 349 | ANDGT; 350 | ANDLE; 351 | ANDLT; 352 | ANDNE; 353 | BITOFF; 354 | BITON; 355 | CAB; 356 | CABEQ; 357 | CABGE; 358 | CABGT; 359 | CABLE; 360 | CABLT; 361 | CABNE; 362 | CALL; 363 | CALLB; 364 | CAS; 365 | CASEQ; 366 | CASGE; 367 | CASGT; 368 | CASLE; 369 | CASLT; 370 | CASNE; 371 | CAT; 372 | CHECK; 373 | CHECKR; 374 | COMP; 375 | DEFINE; 376 | DIV; 377 | DO; 378 | DOUEQ; 379 | DOUGE; 380 | DOUGT; 381 | DOULE; 382 | DOULT; 383 | DOUNE; 384 | DOWEQ; 385 | DOWGE; 386 | DOWGT; 387 | DOWLE; 388 | DOWLT; 389 | DOWNE; 390 | END; 391 | ENDCS; 392 | EXTRCT; 393 | GOTO; 394 | IFEQ; 395 | IFGE; 396 | IFGT; 397 | IFLE; 398 | IFLT; 399 | IFNE; 400 | KFLD; 401 | KLIST; 402 | LOOKUP; 403 | MHHZO; 404 | MHLZO; 405 | MLHZO; 406 | MLLZO; 407 | MOVE; 408 | MOVEA; 409 | MOVEL; 410 | MULT; 411 | MVR; 412 | OCCUR; 413 | OREQ; 414 | ORGE; 415 | ORGT; 416 | ORLE; 417 | ORLT; 418 | ORNE; 419 | PARM; 420 | PLIST; 421 | REALLOC; 422 | SCAN; 423 | SETOFF; 424 | SETON; 425 | SQRT; 426 | SUB; 427 | SUBDUR; 428 | SUBST; 429 | TAG; 430 | TESTB; 431 | TESTN; 432 | TESTZ; 433 | TIME; 434 | WHGE; 435 | WHGT; 436 | WHLE; 437 | WHLT; 438 | WHNE; 439 | XFOOT; 440 | XLATE; 441 | Z-ADD; 442 | Z-SUB; 443 | 444 | 445 | **CTDATA 446 | Line 1 of program data 447 | Line 2 of program data -------------------------------------------------------------------------------- /tests/general/test-free.rpgle: -------------------------------------------------------------------------------- 1 | // Testing RPGLE free and mixed free/fixed 2 | 3 | 4 | /FREE 5 | // Test operators, literals, and constants 6 | x = 2 1 + 2 1 - 2 1 * 2 1 / 2 1 ** 2 7 | x += 1 x -= 1 x *= 1 x /= 1 x **= 2 8 | x > 1 x < 1 x = 1 x <> 1 x <= 1 x >= 1 9 | x=1 and y=1 x=1 or y=1 not x 10 | . , : 2.5 x'AF' 'a string' *ON *OFF *INLR=*ON; 11 | /END-FREE 12 | 13 | 14 | /FREE 15 | // Test control specifications 16 | ctl-opt; 17 | 18 | ctl-opt main(main); //inline comment 19 | /END-FREE 20 | 21 | H* Test control spec 22 | H DATFMT(*YMD) DATEDIT(*YMD) DEBUG(*YES) OPTION(*NODEBUGIO) h spec comment 23 | 24 | ctl-opt option(*srcstmt:*noDebugIO:*nounref) dftActGrp(*no); 25 | 26 | ctl-opt datfmt(*iso) timfmt(*iso) 27 | alwnull(*usrctl); 28 | 29 | ctl-opt option(*srcstmt)ccsid(*char:*jobrun); 30 | 31 | H OPTION(*SRCSTMT : 32 | H *NODEBUGIO) 33 | H ACTGRP(*NEW) 34 | CTL-OPT ALWNULL(*USRCTL) 35 | CCSID(*UCS2 36 | :1200) 37 | CCSID(*CHAR:*JOBRUN); 38 | H DATFMT(*YMD) TIMFMT(*USA) 39 | 40 | 41 | /FREE 42 | // Test file specifications 43 | DCL-F file1a; 44 | DCL-F file1b DISK(*EXT) USAGE(*INPUT); 45 | DCL-F file2 PRINTER; 46 | /END-FREE 47 | 48 | F* Test file spec (externally described) 49 | FANOTHRFILEUPEADE L G SPECIAL INDDS(SOMEDS) f spec comment 50 | 51 | DCL-F file3 SEQ; //inline comment 52 | DCL-F file4 WORKSTN; 53 | DCL-F file5 USAGE(*UPDATE) KEYED; 54 | 55 | F* Test file spec (externally described) 56 | FANOTHRFILEUPEADE L G SPECIAL INDDS(SOMEDS) f spec comment 57 | 58 | dcl-f CLS019B workstn indDs(dspf) usropn; 59 | 60 | 61 | 62 | // Test named constant definition 63 | DCL-C CON_1 CONST(1); //inline comment 64 | DCL-C CON_2 2; 65 | 66 | DCL-C array_total_size 67 | %SIZE(array:*ALL); 68 | 69 | 70 | // Test standalone field definition 71 | DCL-S limit PACKED(5) INZ(100); //inline comment 72 | 73 | D* Test definition spec 74 | DMYFIELD ESS *OPCODE-12345 *12 NOOPT d spec comment 75 | 76 | DCL-S num INZ(0) LIKE(limit); 77 | 78 | 79 | // Test data structure definition 80 | /FREE 81 | dcl-ds resp likeds(geoResponse); 82 | 83 | DCL-DS address; 84 | num int(5); 85 | street VARCHAR(25); 86 | city VARCHAR(25); 87 | province VARCHAR(25); 88 | postcode VARCHAR(6); 89 | END-DS address; 90 | /END-FREE 91 | 92 | DCL-DS person QUALIFIED; 93 | name VARCHAR(25); 94 | DCL-DS address; 95 | num int(5); 96 | street VARCHAR(25); 97 | city VARCHAR(25); 98 | province VARCHAR(25); 99 | postcode VARCHAR(6); 100 | END-DS address; 101 | age int(5); 102 | END-DS person; 103 | 104 | DCL-DS family QUALIFIED; 105 | num int(5); 106 | DCL-DS person DIM(10); 107 | name VARCHAR(25); 108 | age int(5); 109 | numPets int(5); 110 | DCL-DS pets DIM(5); 111 | name VARCHAR(25); 112 | type VARCHAR(25); 113 | END-DS pets; 114 | END-DS person; 115 | END-DS; 116 | 117 | 118 | /FREE 119 | // Test prototypes and procedure interfaces 120 | DCL-PI *N EXTPGM; 121 | name CHAR(10) CONST; 122 | END-PI; 123 | 124 | DCL-PI *N; 125 | id INT(10) VALUE; 126 | quantity INT(10) CONST; 127 | price PACKED(7:2) CONST; 128 | END-PI; 129 | 130 | DCL-PI *N CHAR(10) END-PI; //inline comment 131 | 132 | DCL-PI *N; 133 | DCL-PARM select CHAR(10); 134 | name CHAR(10); 135 | DCL-PARM address CHAR(25); 136 | END-PI; 137 | 138 | DCL-PR myPgm EXTPGM; //inline comment 139 | name CHAR(10) CONST; 140 | END-PR; 141 | 142 | DCL-PR addNewOrder; 143 | id INT(10) CONST; 144 | quantity INT(10) CONST; 145 | price PACKED(7:2) CONST; 146 | END-PR; 147 | 148 | DCL-PR getCurrentUser CHAR(10) END-PR; 149 | 150 | DCL-PR myProc; 151 | DCL-PARM select CHAR(10); 152 | name CHAR(10); 153 | DCL-PARM address CHAR(25); //inline comment 154 | END-PR; 155 | /END-FREE 156 | 157 | 158 | // Testing general 159 | read file; // Get next record 160 | dow not %eof(file); // Keep looping while we have 161 | // a record 162 | if %error; 163 | dsply 'The read failed'; 164 | leave; 165 | else; 166 | chain(n) name database data; 167 | time = hours * num_employees 168 | + overtime_saved; 169 | pos = %scan (',': name); 170 | name = %xlate(upper:lower:name); 171 | exsr handle_record; 172 | read file; 173 | endif; 174 | enddo; 175 | 176 | begsr handle_record; 177 | eval(h) time = time + total_hours_array (empno); 178 | temp_hours = total_hours - excess_hours; 179 | record_transaction(); 180 | endsr; 181 | 182 | 183 | DCL-S name 184 | /IF DEFINED(TRUE) 185 | CHAR(10); 186 | /ELSEIF DEFINED(TRUE OR FALSE) 187 | VARCHAR(10); 188 | /ELSE 189 | CHAR(12); 190 | /ENDIF 191 | 192 | /COPY /something 193 | /INCLUDE /something/else 194 | 195 | 196 | **free 197 | /copy mpkcorsrc,pr_f3gtrtd // comment 198 | dcl-s RLBERRCNT packed(3); // issue #19 199 | dcl-s i like(RLBERRCNT); 200 | 201 | /charcount STDCHARSIZE 202 | 203 | for x = 1 to 10 by 5; 204 | endfor; 205 | 206 | for y in %list( 'a' : 'b' : 'c'); 207 | endfor; 208 | 209 | if (a < b) and (c > d); 210 | endif; 211 | 212 | // Fall 2024 RPGLE enhancements: 213 | 214 | // New BIF's 215 | max = %hival( i ); 216 | min = %loval( i ); 217 | 218 | // New CTL-OPT keyword DATEYY 219 | ctl-opt dateyy(*warn); 220 | 221 | 222 | // Issue #76 223 | // - handle hyphenated opcodes and fields containing opcode words 224 | 225 | dcl-s end1 int(10); 226 | dcl-s endif_b int(10); 227 | dcl-s c_endif int(10); 228 | dcl-s endx int(10); 229 | dcl-s end#1 int(10); 230 | dcl-s end@1 int(10); 231 | dcl-s end$1 int(10); 232 | dcl-s end£1 int(10); 233 | dcl-s end§1 int(10); 234 | dcl-s #end1 int(10); 235 | dcl-s @end1 int(10); 236 | dcl-s $end1 int(10); 237 | dcl-s £end1 int(10); 238 | dcl-s §end1 int(10); 239 | 240 | monitor; // Valid 241 | on-error; // Valid 242 | endmon; // Valid 243 | end-mon; // Invalid 244 | end-monitor; // Invalid 245 | abc-monitor; // Invalid 246 | 247 | end1 = 1; 248 | endif_b = 2; 249 | c_endif = 3; 250 | endx = 4; 251 | end#1 = 5; 252 | end@1 = 6; 253 | end$1 = 7; 254 | end£1 = 8; 255 | end§1 = 9; 256 | #end1 = 5; 257 | @end1 = 6; 258 | $end1 = 7; 259 | £end1 = 8; 260 | §end1 = 9; 261 | 262 | endif; // Valid 263 | endif-abc; // Invalid 264 | endif-test; // Invalid 265 | 266 | acq; // Valid 267 | acq-test; // Invalid 268 | acquire; // Invalid 269 | 270 | Chain(N) CUSCOD CUSTOMERS; 271 | Chain(EN) CUSCOD CUSTOMERS; 272 | 273 | 274 | // PR #162 275 | // - all valid free format opcodes 276 | ACQ; 277 | ALLOC; 278 | BEGSR; 279 | CALLP; 280 | CHAIN; 281 | CLEAR; 282 | CLOSE; 283 | COMMIT; 284 | DATA-GEN; 285 | DATA-INTO; 286 | DEALLOC; 287 | DELETE; 288 | DOU; 289 | DOW; 290 | DSPLY; 291 | DUMP; 292 | ELSE; 293 | ELSEIF; 294 | ENDDO; 295 | ENDFOR; 296 | ENDIF; 297 | ENDMON; 298 | ENDSL; 299 | ENDSR; 300 | EVAL; 301 | EVALR; 302 | EVAL-CORR; 303 | EXCEPT; 304 | EXFMT; 305 | EXSR; 306 | FEOD; 307 | FOR; 308 | FOR-EACH; 309 | FORCE; 310 | IF; 311 | IN; 312 | ITER; 313 | LEAVE; 314 | LEAVESR; 315 | MONITOR; 316 | NEXT; 317 | ON-ERROR; 318 | ON-EXCP; 319 | ON-EXIT; 320 | OPEN; 321 | OTHER; 322 | OUT; 323 | POST; 324 | READ; 325 | READC; 326 | READE; 327 | READP; 328 | READPE; 329 | REL; 330 | RESET; 331 | RETURN; 332 | ROLBK; 333 | SELECT; 334 | SETGT; 335 | SETLL; 336 | SHTDN; 337 | SND-MSG; 338 | SORTA; 339 | TEST; 340 | UNLOCK; 341 | UPDATE; 342 | WHEN; 343 | WHEN-IN; 344 | WHEN-IS; 345 | WRITE; 346 | XML-INTO; 347 | XML-SAX; 348 | 349 | // - all fixed format opcodes that are not valid in free format 350 | ADD; 351 | ADDDUR; 352 | ACQUIRE; 353 | ANDEQ; 354 | ANDGE; 355 | ANDGT; 356 | ANDLE; 357 | ANDLT; 358 | ANDNE; 359 | BITOFF; 360 | BITON; 361 | CAB; 362 | CABEQ; 363 | CABGE; 364 | CABGT; 365 | CABLE; 366 | CABLT; 367 | CABNE; 368 | CALL; 369 | CALLB; 370 | CAS; 371 | CASEQ; 372 | CASGE; 373 | CASGT; 374 | CASLE; 375 | CASLT; 376 | CASNE; 377 | CAT; 378 | CHECK; 379 | CHECKR; 380 | COMP; 381 | DEFINE; 382 | DIV; 383 | DO; 384 | DOUEQ; 385 | DOUGE; 386 | DOUGT; 387 | DOULE; 388 | DOULT; 389 | DOUNE; 390 | DOWEQ; 391 | DOWGE; 392 | DOWGT; 393 | DOWLE; 394 | DOWLT; 395 | DOWNE; 396 | END; 397 | ENDCS; 398 | EXTRCT; 399 | GOTO; 400 | IFEQ; 401 | IFGE; 402 | IFGT; 403 | IFLE; 404 | IFLT; 405 | IFNE; 406 | KFLD; 407 | KLIST; 408 | LOOKUP; 409 | MHHZO; 410 | MHLZO; 411 | MLHZO; 412 | MLLZO; 413 | MOVE; 414 | MOVEA; 415 | MOVEL; 416 | MULT; 417 | MVR; 418 | OCCUR; 419 | OREQ; 420 | ORGE; 421 | ORGT; 422 | ORLE; 423 | ORLT; 424 | ORNE; 425 | PARM; 426 | PLIST; 427 | REALLOC; 428 | SCAN; 429 | SETOFF; 430 | SETON; 431 | SQRT; 432 | SUB; 433 | SUBDUR; 434 | SUBST; 435 | TAG; 436 | TESTB; 437 | TESTN; 438 | TESTZ; 439 | TIME; 440 | WHGE; 441 | WHGT; 442 | WHLE; 443 | WHLT; 444 | WHNE; 445 | XFOOT; 446 | XLATE; 447 | Z-ADD; 448 | Z-SUB; 449 | --------------------------------------------------------------------------------