⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 indent.c

📁 操作系统源代码
💻 C
📖 第 1 页 / 共 3 页
字号:
/** * Copyright (c) 1985 Sun Microsystems, Inc. * Copyright (c) 1980 The Regents of the University of California. * Copyright (c) 1976 Board of Trustees of the University of Illinois. * All rights reserved. * * Redistribution and use in source and binary forms are permitted * provided that the above copyright notice and this paragraph are * duplicated in all such forms and that any documentation, * advertising materials, and other materials related to such * distribution and use acknowledge that the software was developed * by the University of California, Berkeley, the University of Illinois, * Urbana, and Sun Microsystems, Inc.  The name of either University * or Sun Microsystems may not be used to endorse or promote products * derived from this software without specific prior written permission. * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE. *//* ported to MINIX by: Robert R. Hall <hall@pnet01.cts.com>  */#define	PUBLIC#define NAME_SIZE 14#include <ctype.h>#include <string.h>#include <sys/types.h>#include <fcntl.h>#include <unistd.h>#include <stdlib.h>#include <stdio.h>#include "globs.h"#include "codes.h"#include "proto.h"char           *in_name = "Standard Input";	/* will always point to						   name of input file */char           *out_name = "Standard Output";	/* will always point to						   name of output file */char            bakfile[60];void main(argc, argv)   int             argc;   char          **argv;{   extern int      found_err;		/* flag set in diag() on error */   int             dec_ind;		/* current indentation for					   declarations */   int             di_stack[20];	/* a stack of structure					   indentation levels */   int             flushed_nl;		/* used when buffering up					   comments to remember that a					   newline was passed over */   int             force_nl;		/* when true, code must be					   broken */   int             hd_type;		/* used to store type of stmt					   for if (...), for (...), etc */   register int    i;			/* local loop counter */   int             scase;		/* set to true when we see a					   case, so we will know what					   to do with the following					   colon */   int             sp_sw;		/* when true, we are in the					   expressin of if(...),					   while(...), etc. */   int             squest;		/* when this is positive, we					   have seen a ? without the					   matching : in a <c>?<s>:<s>					   construct */   register char  *t_ptr;		/* used for copying tokens */   int             type_code;		/* the type of token, returned					   by lexi */   int             last_else = 0;	/* true iff last keyword was an					   else */   /*-----------------------------------------------*\    |		      INITIALIZATION		      |    \*-----------------------------------------------*/   ps.p_stack[0] = stmt;		/* this is the parser's stack */   ps.last_nl = true;			/* this is true if the last					   thing scanned was a newline */   ps.last_token = semicolon;   combuf = (char *) malloc(bufsize);   labbuf = (char *) malloc(bufsize);   codebuf = (char *) malloc(bufsize);   l_com = combuf + bufsize - 5;   l_lab = labbuf + bufsize - 5;   l_code = codebuf + bufsize - 5;   combuf[0] = codebuf[0] = labbuf[0] = ' ';	/* set up code, label,						   and comment buffers */   combuf[1] = codebuf[1] = labbuf[1] = '\0';   ps.else_if = 1;			/* Default else-if special					   processing to on */   s_lab = e_lab = labbuf + 1;   s_code = e_code = codebuf + 1;   s_com = e_com = combuf + 1;   buf_ptr = buf_end = in_buffer;   line_no = 1;   had_eof = ps.in_decl = ps.decl_on_line = break_comma = false;   sp_sw = force_nl = false;   ps.in_or_st = false;   ps.bl_line = true;   dec_ind = 0;   di_stack[ps.dec_nest = 0] = 0;   ps.want_blank = ps.in_stmt = ps.ind_stmt = false;   scase = ps.pcase = false;   squest = 0;   sc_end = 0;   bp_save = 0;   be_save = 0;   output = 0;   /*--------------------------------------------------*\    |   		COMMAND LINE SCAN		 |    \*--------------------------------------------------*/#ifdef undef   max_col = 78;			/* -l78 */   lineup_to_parens = 1;		/* -lp */   ps.ljust_decl = 0;			/* -ndj */   ps.com_ind = 33;			/* -c33 */   star_comment_cont = 1;		/* -sc */   ps.ind_size = 8;			/* -i8 */   verbose = 0;   ps.decl_indent = 16;			/* -di16 */   ps.indent_parameters = 1;		/* -ip */   ps.decl_com_ind = 0;			/* if this is not set to some					   positive value by an arg, we					   will set this equal to					   ps.com_ind */   btype_2 = 1;				/* -br */   cuddle_else = 1;			/* -ce */   ps.unindent_displace = 0;		/* -d0 */   ps.case_indent = 0;			/* -cli0 */   format_col1_comments = 1;		/* -fc1 */   procnames_start_line = 1;		/* -psl */   proc_calls_space = 0;		/* -npcs */   comment_delimiter_on_blankline = 1;	/* -cdb */   ps.leave_comma = 1;			/* -nbc */#endif   for (i = 1; i < argc; ++i)      if (strcmp(argv[i], "-npro") == 0)	 break;   set_defaults();   if (i >= argc)      set_profile();   for (i = 1; i < argc; ++i)   {      /* look thru args (if any) for changes to defaults */      if (argv[i][0] != '-')      {					/* no flag on parameter */	 if (input == 0)	 {				/* we must have the input file */	    in_name = argv[i];		/* remember name of input file */	    input = fopen(in_name, "r");	    if (input == 0)	    {				/* check for open error */	       fprintf(stderr, "indent: can't open %s\n", argv[i]);	       exit(1);	    }	    continue;	 } else if (output == 0)	 {				/* we have the output file */	    out_name = argv[i];		/* remember name of output file */	    if (strcmp(in_name, out_name) == 0)	    {				/* attempt to overwrite the					   file */	       fprintf(stderr, "indent: input and output files must be different\n");	       exit(1);	    }	    output = fopen(out_name, "w");	    if (output == 0)	    {				/* check for create error */	       fprintf(stderr, "indent: can't create %s\n", argv[i]);	       exit(1);	    }	    continue;	 }	 fprintf(stderr, "indent: unknown parameter: %s\n", argv[i]);	 exit(1);      } else	 set_option(argv[i]);   }					/* end of for */   if (input == 0)   {      fprintf(stderr, "indent: usage: indent file [ outfile ] [ options ]\n");      exit(1);   }   if (output == 0)      if (troff)	 output = stdout;      else      {	 out_name = in_name;	 bakcopy();      }   if (ps.com_ind <= 1)      ps.com_ind = 2;			/* dont put normal comments					   before column 2 */   if (troff)   {      if (bodyf.font[0] == 0)	 parsefont(&bodyf, "R");      if (scomf.font[0] == 0)	 parsefont(&scomf, "I");      if (blkcomf.font[0] == 0)	 blkcomf = scomf, blkcomf.size += 2;      if (boxcomf.font[0] == 0)	 boxcomf = blkcomf;      if (stringf.font[0] == 0)	 parsefont(&stringf, "L");      if (keywordf.font[0] == 0)	 parsefont(&keywordf, "B");      writefdef(&bodyf, 'B');      writefdef(&scomf, 'C');      writefdef(&blkcomf, 'L');      writefdef(&boxcomf, 'X');      writefdef(&stringf, 'S');      writefdef(&keywordf, 'K');   }   if (bk_max_col <= 0)      bk_max_col = max_col;   if (ps.decl_com_ind <= 0)		/* if not specified by user,					   set this */      ps.decl_com_ind = ps.ljust_decl ? (ps.com_ind <= 10 ? 2 : ps.com_ind - 8) : ps.com_ind;   if (continuation_indent == 0)      continuation_indent = ps.ind_size;   fill_buffer();			/* get first batch of stuff					   into input buffer */   parse(semicolon);   {      register char  *p = buf_ptr;      register        col = 1;      while (1)      {	 if (*p == ' ')	    col++;	 else if (*p == '\t')	    col = ((col - 1) & ~7) + 9;	 else	    break;	 p++;      };      if (col > ps.ind_size)	 ps.ind_level = ps.i_l_follow = col / ps.ind_size;   }   if (troff)   {      register char  *p = in_name, *beg = in_name;      while (*p)	 if (*p++ == '/')	    beg = p;      fprintf(output, ".Fn \"%s\"\n", beg);   }   /* START OF MAIN LOOP */   while (1)   {					/* this is the main loop.  it					   will go until we reach eof */      int             is_procname;      type_code = lexi();		/* lexi reads one token.  The					   actual characters read are					   stored in "token". lexi					   returns a code indicating					   the type of token */      is_procname = ps.procname[0];      /* The following code moves everything following an if (), while         (), else, etc. up to the start of the following stmt to a         buffer. This allows proper handling of both kinds of brace         placement. */      flushed_nl = false;      while (ps.search_brace)      {					/* if we scanned an if(),					   while(), etc., we might need					   to copy stuff into a buffer					   we must loop, copying stuff					   into save_com, until we find					   the start of the stmt which					   follows the if, or whatever */	 switch (type_code)	 {	 case newline:	    ++line_no;	    flushed_nl = true;	 case form_feed:	    break;			/* form feeds and newlines					   found here will be ignored */	 case lbrace:			/* this is a brace that starts					   the compound stmt */	    if (sc_end == 0)	    {				/* ignore buffering if a					   comment wasnt stored up */	       ps.search_brace = false;	       goto check_type;	    }	    if (btype_2)	    {	       save_com[0] = '{';	/* we either want to put the					   brace right after the if */	       goto sw_buffer;		/* go to common code to get out					   of this loop */	    }/* * Something is buffered up in save_com, and -bl processing is in effect. * Add the brace after the comment so it will come out on the next line. */	    flushed_nl = 0;	/* comment can start on the same line */	    *sc_end++ = '\n';	/* break line after comment */	    *sc_end++ = '{';	    goto sw_buffer;	 case comment:			/* we have a comment, so we					   must copy it into the buffer */	    if (!flushed_nl || sc_end != 0)	    {	       if (sc_end == 0)	       {			/* if this is the first					   comment, we must set up the					   buffer */		  save_com[0] = save_com[1] = ' ';		  sc_end = &(save_com[2]);	       } else	       {		  *sc_end++ = '\n';	/* add newline between comments */		  *sc_end++ = ' ';		  --line_no;	       }	       *sc_end++ = '/';		/* copy in start of comment */	       *sc_end++ = '*';	       for (;;)	       {			/* loop until we get to the end					   of the comment */		  *sc_end = *buf_ptr++;		  if (buf_ptr >= buf_end)		     fill_buffer();		  if (*sc_end++ == '*' && *buf_ptr == '/')		     break;		/* we are at end of comment */		  if (sc_end >= &(save_com[sc_size]))		  {			/* check for temp buffer					   overflow */		     diag(1, "Internal buffer overflow - Move big comment from right after if, while, or whatever.");		     fflush(output);		     exit(1);		  }	       }	       *sc_end++ = '/';		/* add ending slash */	       if (++buf_ptr >= buf_end)/* get past / in buffer */		  fill_buffer();	       break;	    }	 default:			/* it is the start of a normal					   statment */	    if (flushed_nl)		/* if we flushed a newline,					   make sure it is put back */	       force_nl = true;	    if ((type_code == sp_paren && *token == 'i'		    && last_else && ps.else_if)		|| (type_code == sp_nparen && *token == 'e'		    && e_code != s_code && e_code[-1] == '}'))	       force_nl = false;	    if (sc_end == 0)	    {				/* ignore buffering if comment					   wasnt saved up */	       ps.search_brace = false;	       goto check_type;	    }	    if (force_nl)	    {				/* if we should insert a nl					   here, put it into the buffer */	       force_nl = false;	       --line_no;		/* this will be re-increased					   when the nl is read from the					   buffer */	       *sc_end++ = '\n';	       *sc_end++ = ' ';	       if (verbose && !flushed_nl)	/* print error msg if						   the line was not						   already broken */		  diag(0, "Line broken");	       flushed_nl = false;	    }	    for (t_ptr = token; *t_ptr; ++t_ptr)	       *sc_end++ = *t_ptr;	/* copy token into temp buffer */	    ps.procname[0] = 0;      sw_buffer:	    ps.search_brace = false;	/* stop looking for start of					   stmt */	    bp_save = buf_ptr;		/* save current input buffer */	    be_save = buf_end;	    buf_ptr = save_com;		/* fix so that subsequent calls					   to lexi will take tokens out					   of save_com */	    *sc_end++ = ' ';		/* add trailing blank, just in					   case */	    buf_end = sc_end;	    sc_end = 0;	    break;	 }				/* end of switch */	 if (type_code != 0)		/* we must make this check,					   just in case there was an					   unexpected EOF */	    type_code = lexi();		/* read another token */	 /* if (ps.search_brace) ps.procname[0] = 0; */	 if ((is_procname = ps.procname[0]) && flushed_nl	     && !proc_str_line && ps.in_decl	     && type_code == ident)	    flushed_nl = 0;      }					/* end of while (search_brace) */      last_else = 0;check_type:      if (type_code == 0)      {					/* we got eof */	 if (s_lab != e_lab || s_code != e_code	     || s_com != e_com)		/* must dump end of line */	    dump_line();	 if (ps.tos > 1)		/* check for balanced braces */	    diag(1, "Stuff missing from end of file.");	 if (verbose)	 {	    printf("There were %d output lines and %d comments\n",		   ps.out_lines, ps.out_coms);	    printf("(Lines with comments)/(Lines with code): %6d\n",		   ps.com_lines / code_lines);	 }	 fflush(output);	 exit(found_err);      }      if (	  (type_code != comment) &&	  (type_code != newline) &&

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -