1*0Sstevel@tonic-gate /* 2*0Sstevel@tonic-gate * CDDL HEADER START 3*0Sstevel@tonic-gate * 4*0Sstevel@tonic-gate * The contents of this file are subject to the terms of the 5*0Sstevel@tonic-gate * Common Development and Distribution License, Version 1.0 only 6*0Sstevel@tonic-gate * (the "License"). You may not use this file except in compliance 7*0Sstevel@tonic-gate * with the License. 8*0Sstevel@tonic-gate * 9*0Sstevel@tonic-gate * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 10*0Sstevel@tonic-gate * or http://www.opensolaris.org/os/licensing. 11*0Sstevel@tonic-gate * See the License for the specific language governing permissions 12*0Sstevel@tonic-gate * and limitations under the License. 13*0Sstevel@tonic-gate * 14*0Sstevel@tonic-gate * When distributing Covered Code, include this CDDL HEADER in each 15*0Sstevel@tonic-gate * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 16*0Sstevel@tonic-gate * If applicable, add the following below this CDDL HEADER, with the 17*0Sstevel@tonic-gate * fields enclosed by brackets "[]" replaced with your own identifying 18*0Sstevel@tonic-gate * information: Portions Copyright [yyyy] [name of copyright owner] 19*0Sstevel@tonic-gate * 20*0Sstevel@tonic-gate * CDDL HEADER END 21*0Sstevel@tonic-gate */ 22*0Sstevel@tonic-gate /* 23*0Sstevel@tonic-gate * Copyright 2005 Sun Microsystems, Inc. 24*0Sstevel@tonic-gate * All rights reserved. 25*0Sstevel@tonic-gate * Use is subject to license terms. 26*0Sstevel@tonic-gate */ 27*0Sstevel@tonic-gate 28*0Sstevel@tonic-gate /* Copyright (c) 1988 AT&T */ 29*0Sstevel@tonic-gate /* All Rights Reserved */ 30*0Sstevel@tonic-gate 31*0Sstevel@tonic-gate /* Copyright 1976, Bell Telephone Laboratories, Inc. */ 32*0Sstevel@tonic-gate 33*0Sstevel@tonic-gate #pragma ident "%Z%%M% %I% %E% SMI" 34*0Sstevel@tonic-gate 35*0Sstevel@tonic-gate #include <string.h> 36*0Sstevel@tonic-gate #include "once.h" 37*0Sstevel@tonic-gate #include "sgs.h" 38*0Sstevel@tonic-gate #include <locale.h> 39*0Sstevel@tonic-gate #include <limits.h> 40*0Sstevel@tonic-gate 41*0Sstevel@tonic-gate static wchar_t L_INITIAL[] = {'I', 'N', 'I', 'T', 'I', 'A', 'L', 0}; 42*0Sstevel@tonic-gate 43*0Sstevel@tonic-gate char run_directory[PATH_MAX]; 44*0Sstevel@tonic-gate char current_work_directory[PATH_MAX]; 45*0Sstevel@tonic-gate extern int find_run_directory(char *, char *, char *, char **, char *); 46*0Sstevel@tonic-gate 47*0Sstevel@tonic-gate static void get1core(void); 48*0Sstevel@tonic-gate static void free1core(void); 49*0Sstevel@tonic-gate static void get2core(void); 50*0Sstevel@tonic-gate static void free2core(void); 51*0Sstevel@tonic-gate static void get3core(void); 52*0Sstevel@tonic-gate #ifdef DEBUG 53*0Sstevel@tonic-gate static void free3core(void); 54*0Sstevel@tonic-gate #endif 55*0Sstevel@tonic-gate 56*0Sstevel@tonic-gate int 57*0Sstevel@tonic-gate main(int argc, char **argv) 58*0Sstevel@tonic-gate { 59*0Sstevel@tonic-gate int i; 60*0Sstevel@tonic-gate int c; 61*0Sstevel@tonic-gate char *path = NULL; 62*0Sstevel@tonic-gate Boolean eoption = 0, woption = 0; 63*0Sstevel@tonic-gate 64*0Sstevel@tonic-gate sargv = argv; 65*0Sstevel@tonic-gate sargc = argc; 66*0Sstevel@tonic-gate setlocale(LC_ALL, ""); 67*0Sstevel@tonic-gate #ifdef DEBUG 68*0Sstevel@tonic-gate while ((c = getopt(argc, argv, "dyctvnewVQ:Y:")) != EOF) { 69*0Sstevel@tonic-gate #else 70*0Sstevel@tonic-gate while ((c = getopt(argc, argv, "ctvnewVQ:Y:")) != EOF) { 71*0Sstevel@tonic-gate #endif 72*0Sstevel@tonic-gate switch (c) { 73*0Sstevel@tonic-gate #ifdef DEBUG 74*0Sstevel@tonic-gate case 'd': 75*0Sstevel@tonic-gate debug++; 76*0Sstevel@tonic-gate break; 77*0Sstevel@tonic-gate case 'y': 78*0Sstevel@tonic-gate yydebug = TRUE; 79*0Sstevel@tonic-gate break; 80*0Sstevel@tonic-gate #endif 81*0Sstevel@tonic-gate case 'V': 82*0Sstevel@tonic-gate (void) fprintf(stderr, "lex: %s %s\n", 83*0Sstevel@tonic-gate (const char *)SGU_PKG, 84*0Sstevel@tonic-gate (const char *)SGU_REL); 85*0Sstevel@tonic-gate break; 86*0Sstevel@tonic-gate case 'Q': 87*0Sstevel@tonic-gate v_stmp = optarg; 88*0Sstevel@tonic-gate if (*v_stmp != 'y' && *v_stmp != 'n') 89*0Sstevel@tonic-gate error( 90*0Sstevel@tonic-gate "lex: -Q should be followed by [y/n]"); 91*0Sstevel@tonic-gate break; 92*0Sstevel@tonic-gate case 'Y': 93*0Sstevel@tonic-gate path = (char *)malloc(strlen(optarg) + 94*0Sstevel@tonic-gate sizeof ("/nceucform") + 1); 95*0Sstevel@tonic-gate path = strcpy(path, optarg); 96*0Sstevel@tonic-gate break; 97*0Sstevel@tonic-gate case 'c': 98*0Sstevel@tonic-gate ratfor = FALSE; 99*0Sstevel@tonic-gate break; 100*0Sstevel@tonic-gate case 't': 101*0Sstevel@tonic-gate fout = stdout; 102*0Sstevel@tonic-gate break; 103*0Sstevel@tonic-gate case 'v': 104*0Sstevel@tonic-gate report = 1; 105*0Sstevel@tonic-gate break; 106*0Sstevel@tonic-gate case 'n': 107*0Sstevel@tonic-gate report = 0; 108*0Sstevel@tonic-gate break; 109*0Sstevel@tonic-gate case 'w': 110*0Sstevel@tonic-gate case 'W': 111*0Sstevel@tonic-gate woption = 1; 112*0Sstevel@tonic-gate handleeuc = 1; 113*0Sstevel@tonic-gate widecio = 1; 114*0Sstevel@tonic-gate break; 115*0Sstevel@tonic-gate case 'e': 116*0Sstevel@tonic-gate case 'E': 117*0Sstevel@tonic-gate eoption = 1; 118*0Sstevel@tonic-gate handleeuc = 1; 119*0Sstevel@tonic-gate widecio = 0; 120*0Sstevel@tonic-gate break; 121*0Sstevel@tonic-gate default: 122*0Sstevel@tonic-gate (void) fprintf(stderr, 123*0Sstevel@tonic-gate "Usage: lex [-ewctvnVY] [-Q(y/n)] [file]\n"); 124*0Sstevel@tonic-gate exit(1); 125*0Sstevel@tonic-gate } 126*0Sstevel@tonic-gate } 127*0Sstevel@tonic-gate if (woption && eoption) { 128*0Sstevel@tonic-gate error( 129*0Sstevel@tonic-gate "You may not specify both -w and -e simultaneously."); 130*0Sstevel@tonic-gate } 131*0Sstevel@tonic-gate no_input = argc - optind; 132*0Sstevel@tonic-gate if (no_input) { 133*0Sstevel@tonic-gate /* XCU4: recognize "-" file operand for stdin */ 134*0Sstevel@tonic-gate if (strcmp(argv[optind], "-") == 0) 135*0Sstevel@tonic-gate fin = stdin; 136*0Sstevel@tonic-gate else { 137*0Sstevel@tonic-gate fin = fopen(argv[optind], "r"); 138*0Sstevel@tonic-gate if (fin == NULL) 139*0Sstevel@tonic-gate error( 140*0Sstevel@tonic-gate "Can't open input file -- %s", argv[optind]); 141*0Sstevel@tonic-gate } 142*0Sstevel@tonic-gate } else 143*0Sstevel@tonic-gate fin = stdin; 144*0Sstevel@tonic-gate 145*0Sstevel@tonic-gate /* may be gotten: def, subs, sname, schar, ccl, dchar */ 146*0Sstevel@tonic-gate (void) gch(); 147*0Sstevel@tonic-gate 148*0Sstevel@tonic-gate /* may be gotten: name, left, right, nullstr, parent */ 149*0Sstevel@tonic-gate get1core(); 150*0Sstevel@tonic-gate 151*0Sstevel@tonic-gate scopy(L_INITIAL, sp); 152*0Sstevel@tonic-gate sname[0] = sp; 153*0Sstevel@tonic-gate sp += slength(L_INITIAL) + 1; 154*0Sstevel@tonic-gate sname[1] = 0; 155*0Sstevel@tonic-gate 156*0Sstevel@tonic-gate /* XCU4: %x exclusive start */ 157*0Sstevel@tonic-gate exclusive[0] = 0; 158*0Sstevel@tonic-gate 159*0Sstevel@tonic-gate if (!handleeuc) { 160*0Sstevel@tonic-gate /* 161*0Sstevel@tonic-gate * Set ZCH and ncg to their default values 162*0Sstevel@tonic-gate * as they may be needed to handle %t directive. 163*0Sstevel@tonic-gate */ 164*0Sstevel@tonic-gate ZCH = ncg = NCH; /* ncg behaves as constant in this mode. */ 165*0Sstevel@tonic-gate } 166*0Sstevel@tonic-gate 167*0Sstevel@tonic-gate /* may be disposed of: def, subs, dchar */ 168*0Sstevel@tonic-gate if (yyparse()) 169*0Sstevel@tonic-gate exit(1); /* error return code */ 170*0Sstevel@tonic-gate 171*0Sstevel@tonic-gate if (handleeuc) { 172*0Sstevel@tonic-gate ncg = ncgidtbl * 2; 173*0Sstevel@tonic-gate ZCH = ncg; 174*0Sstevel@tonic-gate if (ncg >= MAXNCG) 175*0Sstevel@tonic-gate error( 176*0Sstevel@tonic-gate "Too complex rules -- requires too many char groups."); 177*0Sstevel@tonic-gate sortcgidtbl(); 178*0Sstevel@tonic-gate } 179*0Sstevel@tonic-gate repbycgid(); /* Call this even in ASCII compat. mode. */ 180*0Sstevel@tonic-gate 181*0Sstevel@tonic-gate /* 182*0Sstevel@tonic-gate * maybe get: 183*0Sstevel@tonic-gate * tmpstat, foll, positions, gotof, nexts, 184*0Sstevel@tonic-gate * nchar, state, atable, sfall, cpackflg 185*0Sstevel@tonic-gate */ 186*0Sstevel@tonic-gate free1core(); 187*0Sstevel@tonic-gate get2core(); 188*0Sstevel@tonic-gate ptail(); 189*0Sstevel@tonic-gate mkmatch(); 190*0Sstevel@tonic-gate #ifdef DEBUG 191*0Sstevel@tonic-gate if (debug) 192*0Sstevel@tonic-gate pccl(); 193*0Sstevel@tonic-gate #endif 194*0Sstevel@tonic-gate sect = ENDSECTION; 195*0Sstevel@tonic-gate if (tptr > 0) 196*0Sstevel@tonic-gate cfoll(tptr-1); 197*0Sstevel@tonic-gate #ifdef DEBUG 198*0Sstevel@tonic-gate if (debug) 199*0Sstevel@tonic-gate pfoll(); 200*0Sstevel@tonic-gate #endif 201*0Sstevel@tonic-gate cgoto(); 202*0Sstevel@tonic-gate #ifdef DEBUG 203*0Sstevel@tonic-gate if (debug) { 204*0Sstevel@tonic-gate (void) printf("Print %d states:\n", stnum + 1); 205*0Sstevel@tonic-gate for (i = 0; i <= stnum; i++) 206*0Sstevel@tonic-gate stprt(i); 207*0Sstevel@tonic-gate } 208*0Sstevel@tonic-gate #endif 209*0Sstevel@tonic-gate /* 210*0Sstevel@tonic-gate * may be disposed of: 211*0Sstevel@tonic-gate * positions, tmpstat, foll, state, name, 212*0Sstevel@tonic-gate * left, right, parent, ccl, schar, sname 213*0Sstevel@tonic-gate * maybe get: verify, advance, stoff 214*0Sstevel@tonic-gate */ 215*0Sstevel@tonic-gate free2core(); 216*0Sstevel@tonic-gate get3core(); 217*0Sstevel@tonic-gate layout(); 218*0Sstevel@tonic-gate /* 219*0Sstevel@tonic-gate * may be disposed of: 220*0Sstevel@tonic-gate * verify, advance, stoff, nexts, nchar, 221*0Sstevel@tonic-gate * gotof, atable, ccpackflg, sfall 222*0Sstevel@tonic-gate */ 223*0Sstevel@tonic-gate 224*0Sstevel@tonic-gate #ifdef DEBUG 225*0Sstevel@tonic-gate free3core(); 226*0Sstevel@tonic-gate #endif 227*0Sstevel@tonic-gate if (path == NULL) { 228*0Sstevel@tonic-gate current_work_directory[0] = '.'; 229*0Sstevel@tonic-gate current_work_directory[1] = '\0'; 230*0Sstevel@tonic-gate if (find_run_directory(sargv[0], 231*0Sstevel@tonic-gate current_work_directory, 232*0Sstevel@tonic-gate run_directory, 233*0Sstevel@tonic-gate (char **)0, 234*0Sstevel@tonic-gate getenv("PATH")) != 0) { 235*0Sstevel@tonic-gate (void) fprintf(stderr, 236*0Sstevel@tonic-gate "Error in finding run directory. Using default %s\n", 237*0Sstevel@tonic-gate current_work_directory); 238*0Sstevel@tonic-gate path = current_work_directory; 239*0Sstevel@tonic-gate } else { 240*0Sstevel@tonic-gate path = run_directory; 241*0Sstevel@tonic-gate } 242*0Sstevel@tonic-gate } 243*0Sstevel@tonic-gate 244*0Sstevel@tonic-gate if (handleeuc) { 245*0Sstevel@tonic-gate if (ratfor) 246*0Sstevel@tonic-gate error("Ratfor is not supported by -w or -e option."); 247*0Sstevel@tonic-gate (void) strcat(path, "/nceucform"); 248*0Sstevel@tonic-gate } 249*0Sstevel@tonic-gate else 250*0Sstevel@tonic-gate (void) strcat(path, ratfor ? "/nrform" : "/ncform"); 251*0Sstevel@tonic-gate 252*0Sstevel@tonic-gate fother = fopen(path, "r"); 253*0Sstevel@tonic-gate if (fother == NULL) 254*0Sstevel@tonic-gate error("Lex driver missing, file %s", path); 255*0Sstevel@tonic-gate while ((i = getc(fother)) != EOF) 256*0Sstevel@tonic-gate (void) putc((char)i, fout); 257*0Sstevel@tonic-gate (void) fclose(fother); 258*0Sstevel@tonic-gate (void) fclose(fout); 259*0Sstevel@tonic-gate if (report == 1) 260*0Sstevel@tonic-gate statistics(); 261*0Sstevel@tonic-gate (void) fclose(stdout); 262*0Sstevel@tonic-gate (void) fclose(stderr); 263*0Sstevel@tonic-gate return (0); /* success return code */ 264*0Sstevel@tonic-gate } 265*0Sstevel@tonic-gate 266*0Sstevel@tonic-gate static void 267*0Sstevel@tonic-gate get1core(void) 268*0Sstevel@tonic-gate { 269*0Sstevel@tonic-gate ccptr = ccl = (CHR *)myalloc(CCLSIZE, sizeof (*ccl)); 270*0Sstevel@tonic-gate pcptr = pchar = (CHR *)myalloc(pchlen, sizeof (*pchar)); 271*0Sstevel@tonic-gate def = (CHR **)myalloc(DEFSIZE, sizeof (*def)); 272*0Sstevel@tonic-gate subs = (CHR **)myalloc(DEFSIZE, sizeof (*subs)); 273*0Sstevel@tonic-gate dp = dchar = (CHR *)myalloc(DEFCHAR, sizeof (*dchar)); 274*0Sstevel@tonic-gate sname = (CHR **)myalloc(STARTSIZE, sizeof (*sname)); 275*0Sstevel@tonic-gate /* XCU4: exclusive start array */ 276*0Sstevel@tonic-gate exclusive = (int *)myalloc(STARTSIZE, sizeof (*exclusive)); 277*0Sstevel@tonic-gate sp = schar = (CHR *)myalloc(STARTCHAR, sizeof (*schar)); 278*0Sstevel@tonic-gate if (ccl == 0 || def == 0 || 279*0Sstevel@tonic-gate pchar == 0 || subs == 0 || dchar == 0 || 280*0Sstevel@tonic-gate sname == 0 || exclusive == 0 || schar == 0) 281*0Sstevel@tonic-gate error("Too little core to begin"); 282*0Sstevel@tonic-gate } 283*0Sstevel@tonic-gate 284*0Sstevel@tonic-gate static void 285*0Sstevel@tonic-gate free1core(void) 286*0Sstevel@tonic-gate { 287*0Sstevel@tonic-gate free(def); 288*0Sstevel@tonic-gate free(subs); 289*0Sstevel@tonic-gate free(dchar); 290*0Sstevel@tonic-gate } 291*0Sstevel@tonic-gate 292*0Sstevel@tonic-gate static void 293*0Sstevel@tonic-gate get2core(void) 294*0Sstevel@tonic-gate { 295*0Sstevel@tonic-gate int i; 296*0Sstevel@tonic-gate gotof = (int *)myalloc(nstates, sizeof (*gotof)); 297*0Sstevel@tonic-gate nexts = (int *)myalloc(ntrans, sizeof (*nexts)); 298*0Sstevel@tonic-gate nchar = (CHR *)myalloc(ntrans, sizeof (*nchar)); 299*0Sstevel@tonic-gate state = (int **)myalloc(nstates, sizeof (*state)); 300*0Sstevel@tonic-gate atable = (int *)myalloc(nstates, sizeof (*atable)); 301*0Sstevel@tonic-gate sfall = (int *)myalloc(nstates, sizeof (*sfall)); 302*0Sstevel@tonic-gate cpackflg = (Boolean *)myalloc(nstates, sizeof (*cpackflg)); 303*0Sstevel@tonic-gate tmpstat = (CHR *)myalloc(tptr+1, sizeof (*tmpstat)); 304*0Sstevel@tonic-gate foll = (int **)myalloc(tptr+1, sizeof (*foll)); 305*0Sstevel@tonic-gate nxtpos = positions = (int *)myalloc(maxpos, sizeof (*positions)); 306*0Sstevel@tonic-gate if (tmpstat == 0 || foll == 0 || positions == 0 || 307*0Sstevel@tonic-gate gotof == 0 || nexts == 0 || nchar == 0 || 308*0Sstevel@tonic-gate state == 0 || atable == 0 || sfall == 0 || cpackflg == 0) 309*0Sstevel@tonic-gate error("Too little core for state generation"); 310*0Sstevel@tonic-gate for (i = 0; i <= tptr; i++) 311*0Sstevel@tonic-gate foll[i] = 0; 312*0Sstevel@tonic-gate } 313*0Sstevel@tonic-gate 314*0Sstevel@tonic-gate static void 315*0Sstevel@tonic-gate free2core(void) 316*0Sstevel@tonic-gate { 317*0Sstevel@tonic-gate free(positions); 318*0Sstevel@tonic-gate free(tmpstat); 319*0Sstevel@tonic-gate free(foll); 320*0Sstevel@tonic-gate free(name); 321*0Sstevel@tonic-gate free(left); 322*0Sstevel@tonic-gate free(right); 323*0Sstevel@tonic-gate free(parent); 324*0Sstevel@tonic-gate free(nullstr); 325*0Sstevel@tonic-gate free(state); 326*0Sstevel@tonic-gate free(sname); 327*0Sstevel@tonic-gate /* XCU4: exclusive start array */ 328*0Sstevel@tonic-gate free(exclusive); 329*0Sstevel@tonic-gate free(schar); 330*0Sstevel@tonic-gate free(ccl); 331*0Sstevel@tonic-gate } 332*0Sstevel@tonic-gate 333*0Sstevel@tonic-gate static void 334*0Sstevel@tonic-gate get3core(void) 335*0Sstevel@tonic-gate { 336*0Sstevel@tonic-gate verify = (int *)myalloc(outsize, sizeof (*verify)); 337*0Sstevel@tonic-gate advance = (int *)myalloc(outsize, sizeof (*advance)); 338*0Sstevel@tonic-gate stoff = (int *)myalloc(stnum+2, sizeof (*stoff)); 339*0Sstevel@tonic-gate if (verify == 0 || advance == 0 || stoff == 0) 340*0Sstevel@tonic-gate error("Too little core for final packing"); 341*0Sstevel@tonic-gate } 342*0Sstevel@tonic-gate 343*0Sstevel@tonic-gate #ifdef DEBUG 344*0Sstevel@tonic-gate static void 345*0Sstevel@tonic-gate free3core(void) 346*0Sstevel@tonic-gate { 347*0Sstevel@tonic-gate free(advance); 348*0Sstevel@tonic-gate free(verify); 349*0Sstevel@tonic-gate free(stoff); 350*0Sstevel@tonic-gate free(gotof); 351*0Sstevel@tonic-gate free(nexts); 352*0Sstevel@tonic-gate free(nchar); 353*0Sstevel@tonic-gate free(atable); 354*0Sstevel@tonic-gate free(sfall); 355*0Sstevel@tonic-gate free(cpackflg); 356*0Sstevel@tonic-gate } 357*0Sstevel@tonic-gate #endif 358*0Sstevel@tonic-gate 359*0Sstevel@tonic-gate BYTE * 360*0Sstevel@tonic-gate myalloc(int a, int b) 361*0Sstevel@tonic-gate { 362*0Sstevel@tonic-gate BYTE *i; 363*0Sstevel@tonic-gate i = calloc(a, b); 364*0Sstevel@tonic-gate if (i == 0) 365*0Sstevel@tonic-gate warning("calloc returns a 0"); 366*0Sstevel@tonic-gate return (i); 367*0Sstevel@tonic-gate } 368*0Sstevel@tonic-gate 369*0Sstevel@tonic-gate void 370*0Sstevel@tonic-gate yyerror(char *s) 371*0Sstevel@tonic-gate { 372*0Sstevel@tonic-gate (void) fprintf(stderr, 373*0Sstevel@tonic-gate "\"%s\":line %d: Error: %s\n", sargv[optind], yyline, s); 374*0Sstevel@tonic-gate } 375