home *** CD-ROM | disk | FTP | other *** search
- /*
- * Diverses fonctions de base
- * (c)1991 par Denis GOUNELLE
- */
-
- #include "aroff.h"
- #include "pile.h"
-
- static unsigned char tmp[1+LGMAXSTR<<1], aux[LGMAXSTR+1] ;
-
- extern struct Contexte *LastContext ;
- extern struct String *CurrentString ;
- extern unsigned char Arg[], OutputBuf[] ;
- extern char *ARoff_Version, *ARoff_Usage ;
- extern struct InputFile *CurrentInputFile ;
- extern struct Macro *CurrentMacro, *FindVar() ;
- extern struct TeteListe TReg, TStr, TMac, TTrp ;
- extern long ArgLen, OutputLen, TotalIndent, LineSpacing, LineNumber,
- NumInterv, NumSpace, NumIndent, PageOffset, Flg, TmpNoNum,
- InputMode, TmpIndent, OutputLine, PageLen, PageNumber,
- EmptyToWrite, NewPageNumber ;
-
- extern void do_ab(), do_ad(), do_am(), do_as(), do_bp(), do_br(), do_ce(),
- do_de(), do_ds(), do_el(), do_ex(), do_fi(), do_fs(), do_fl(),
- do_if(), do_in(), do_ll(), do_ls(), do_lt(), do_na(), do_ne(),
- do_nf(), do_nm(), do_nn(), do_nr(), do_pl(), do_pm(), do_pn(),
- do_po(), do_rm(), do_rr(), do_rs(), do_rt(), do_so(), do_sp(),
- do_ta(), do_tc(), do_ti(), do_tl(), do_tm(), do_tr(), do_ts(),
- do_wh() ;
-
- /**************************************************************************/
-
- void Termine()
- {
- register long k ;
- register struct Macro *m ;
-
- CloseFile( CurrentInputFile ) ;
-
- VideListe( &TReg ) ;
- VideListe( &TStr ) ;
- VideListe( &TTrp ) ;
-
- for ( m = (struct Macro *)TMac.tl_Premier ;
- m ;
- m = (struct Macro *)m->m_Node.el_Suivant )
- {
- VideListe( &(m->m_Def) ) ;
- for ( k = 0 ; m->m_Arg[k] ; k++ ) free( m->m_Arg[k] ) ;
- }
- VideListe( &TMac ) ;
-
- exit( 0 ) ;
- }
-
- /**************************************************************************/
-
- void Abort( indic )
- long indic ;
-
- {
- if ( (indic) && (OutputLen) )
- {
- OutputBuf[OutputLen] = '\0' ;
- OutputLen = '\0' ;
- LigneSuiv( OutputBuf ) ;
- }
- Termine() ;
- }
-
- /**************************************************************************/
-
- void FatalError( code , line , file )
- long code, line ;
- char *file ;
-
- {
- if ( code == ERR_ARGS )
- fprintf( stderr , "%s\n%s\n" , ARoff_Version , ARoff_Usage ) ;
- else
- {
- fprintf( stderr , "Error %d in file %s at line %d\n" , code , file , line ) ;
- if ( CurrentInputFile )
- fprintf( stderr , "current file: %s, line: %d\n" ,
- CurrentInputFile->if_Name , CurrentInputFile->if_Line ) ;
- }
-
- Abort( 0 ) ;
- }
-
- /**************************************************************************/
-
- char *myalloc( len , indic )
- register long len ;
- long indic ;
-
- {
- register long *p ;
-
- if (! len) Fatal( ERR_INTERNAL ) ;
-
- if ( len & 1 ) len++ ; /* forces len to next even value */
- p = (long *)malloc( len ) ;
- if ( ! p ) Fatal( ERR_MEMORY ) ;
- if ( indic ) bzero( p , len ) ;
- return( (char *)p ) ;
- }
-
- /**************************************************************************/
-
- void SetMacArgs()
- {
- register long k ;
- register struct Macro *m ;
- register unsigned char *p, c ;
-
- m = CurrentMacro ;
- m->m_NbArg = k = 0 ;
-
- while ( Arg[k] )
- {
- p = m->m_Arg[m->m_NbArg] = (unsigned char *)myalloc( ArgLen - k + 1 , 0 ) ;
- while ( (c = Arg[k]) && (! isspace( c )) )
- {
- if ( c == SC_FIXSPC ) c = ' ' ;
- *p = c ;
- k++ ;
- p++ ;
- }
- *p = '\0' ;
- while ( isspace( Arg[k] ) ) k++ ;
- m->m_NbArg++ ;
- }
-
- SetReg( ".$" , m->m_NbArg , 0 ) ;
- }
-
- /**************************************************************************/
-
- struct Command CmdTable[] =
- {
- "ab",do_ab,
- "ad",do_ad,
- "am",do_am,
- "as",do_as,
- "bp",do_bp,
- "br",do_br,
- "ce",do_ce,
- "de",do_de,
- "ds",do_ds,
- "el",do_el,
- "ex",do_ex,
- "fi",do_fi,
- /*"fl",do_fl, inaccessible pour l'utilisateur */
- "fs",do_fs,
- "if",do_if,
- "in",do_in,
- "ll",do_ll,
- "ls",do_ls,
- "lt",do_lt,
- "na",do_na,
- "ne",do_ne,
- "nf",do_nf,
- "nm",do_nm,
- "nn",do_nn,
- "nr",do_nr,
- "pl",do_pl,
- "pm",do_pm,
- "pn",do_pn,
- "po",do_po,
- "rm",do_rm,
- "rr",do_rr,
- "rs",do_rs,
- "rt",do_rt,
- "so",do_so,
- "sp",do_sp,
- "ta",do_ta,
- "tc",do_tc,
- "ti",do_ti,
- "tl",do_tl,
- "tm",do_tm,
- "tr",do_tr,
- "ts",do_ts,
- "wh",do_wh,
- "" ,NULL,
- } ;
-
- void ExecCmd( cmd )
- char *cmd ;
-
- {
- register struct Macro *m ;
- register struct Command *p ;
-
- Arg[ArgLen] = '\0' ;
-
- /* est-ce une requete ? */
-
- for ( p = CmdTable ; p->c_func ; p++ )
- if (! strcmp( p->c_name , cmd ))
- {
- (*p->c_func)() ;
- goto _end ;
- }
-
- /* est-ce une macro ? */
-
- m = FindVar( &TMac , cmd ) ;
- if ( m )
- {
- if ( InputMode & IM_EXMACRO ) Push( TE_MACRO , CurrentMacro ) ;
- if ( InputMode & IM_STRING ) Push( TE_STRING , CurrentString ) ;
- Push( TE_INMODE , InputMode ) ;
- BCLR( InputMode , (IM_STRING|IM_EXMACRO) ) ;
-
- m->m_NextC = 0 ;
- m->m_NextL = (struct MLine *)m->m_Def.tl_Premier ;
- CurrentMacro = m ;
- SetMacArgs() ;
- BSET( InputMode , IM_EXMACRO ) ;
- }
-
- _end:
-
- if ( (Flg & F_WASIF) && (strcmp( cmd , "if")) ) BCLR( Flg , F_WASIF ) ;
- BCLR( Flg , F_NOBRK ) ;
- BSET( Flg , (F_MACREQ|F_WASNL) ) ;
- }
-
- /**************************************************************************/
-
- long GetName( dst )
- char *dst ;
-
- {
- long c ;
-
- if ( (c = GetChar()) == EOF ) return( 0 ) ;
- dst[0] = c ;
- if ( (c = GetChar()) == EOF ) return( 0 ) ;
- dst[1] = c ;
- dst[2] = '\0' ;
- return( 1 ) ;
- }
-
- /**************************************************************************/
-
- long myatoi()
-
- {
- long k ;
- unsigned char *p ;
-
- k = strtol( Arg , &p , 10 ) ;
- if ( (*p != '\0') && (! isspace( *p )) ) Fatal( ERR_SYNTAX ) ;
- return( k ) ;
- }
-
- /**************************************************************************/
-
- char *GetArg( pstr , pval )
- unsigned char *pstr ;
- long *pval ;
-
- {
- while ( isspace( *pstr ) ) pstr++ ;
- if ( isdigit( *pstr ) ) *pval = atoi( pstr ) ;
- while ( (*pstr != '\0') && (! isspace( *pstr)) ) pstr++ ;
- return( pstr ) ;
- }
-
- /**************************************************************************/
-
- long ChangeValue( val )
- long *val ;
-
- {
- register char c ;
- register long k ;
-
- k = 0 ;
- c = '\0' ;
- if ( (Arg[k] == '+') || (Arg[k] == '-') )
- {
- c = Arg[k] ;
- k++ ;
- }
-
- if (! isdigit( Arg[k] )) return( 0 ) ;
- k = atoi( &Arg[k] ) ;
-
- switch ( c )
- {
- case '+' : *val += k ; break ;
- case '-' : *val -= k ; break ;
- default : *val = k ; break ;
- }
-
- return( 1 ) ;
- }
-
- /**************************************************************************/
-
- void ChangePageNumber( number )
- long number ;
-
- {
- PageNumber = number ;
- SetReg( "pn" , PageNumber , 0 ) ;
- NewPageNumber = number + 1 ;
- }
-
- /**************************************************************************/
-
- long LigneSuiv( str )
- char *str ;
-
- {
- register long k ;
- register char *p ;
- register struct Macro *m ;
-
- m = CurrentMacro ;
- k = strlen( str ) ;
-
- if ( TestTrp( OutputLine ) )
- {
- BSET( Flg , F_TRAP ) ;
- BSET( CurrentMacro->m_Flag , MF_TRAP ) ;
- p = myalloc( k+1 , 0 ) ;
- strcpy( p , str ) ;
- Push( TE_OUTLINE , p ) ;
- Push( TE_TOWRITE , EmptyToWrite ) ;
- if ( m ) BSET( m->m_Flag , MF_WAIT ) ;
- EmptyToWrite = 0 ;
- return ;
- }
-
- if ( k ) do_fl( str ) ;
- OutputLine++ ;
- if ( OutputLine > PageLen )
- {
- OutputLine = 1 ;
- ChangePageNumber( NewPageNumber ) ;
- }
-
- }
-
- /**************************************************************************/
-
- void WriteLine()
-
- {
- register long k ;
- register unsigned char *p ;
-
- /* ajoute le decalage de page */
-
- p = tmp ;
- for ( k = 0 ; k < PageOffset ; k++ , p++ ) *p = ' ' ;
-
- /* effectue la numerotation */
-
- for ( k = 0 ; k < OutputLen ; k++ ) if (! isspace( OutputBuf[k] )) break ;
- if ( (Flg & F_NUMBER) && (k < OutputLen) && (! TmpNoNum) )
- {
- for ( k = 0 ; k < NumIndent ; k++ , p++ ) *p = ' ' ;
- sprintf( aux , "%d" , LineNumber ) ;
- LineNumber++ ;
- SetReg( "ol" , LineNumber , 0 ) ;
- if ( (NumInterv != 1) && ((LineNumber % NumInterv) != 1) )
- for ( k = 0 ; aux[k] != '\0' ; k++ ) aux[k] = ' ' ;
- strcpy( p , aux ) ;
- p += strlen( aux ) ;
- for ( k = 0 ; k < NumSpace ; k++ , p++ ) *p = ' ' ;
- }
-
- /* ajoute l'indentation */
-
- for ( k = 0 ; k < TotalIndent ; k++ , p++ ) *p = ' ' ;
- if ( Flg & F_NOTI ) TmpIndent = 0 ;
-
- /* ecrit la ligne finale */
-
- bcopy( OutputBuf , p , OutputLen ) ;
- p += OutputLen ;
- OutputLen = 0 ;
- *p = '\n' ;
- p[1] = '\0' ;
-
- EmptyToWrite += LineSpacing - 1 ;
- LigneSuiv( tmp ) ;
- }
-
- /**************************************************************************/
-
- void SauveContexte( indic )
- long indic ;
-
- {
- register long k ;
- register struct Macro *m ;
- register struct Contexte *p ;
-
- p = (struct Contexte *)myalloc( sizeof(struct Contexte) , 0 ) ;
-
- if ( InputMode & IM_EXMACRO )
- {
- m = CurrentMacro ;
- bcopy( m , &(p->src.c_macro) , sizeof(struct Macro) ) ;
- p->c_ptr = (long)m ;
- p->c_len = sizeof(struct Macro) ;
- }
- else if ( InputMode & IM_STRING )
- {
- k = 9 + CurrentString->s_len ;
- bcopy( CurrentString , &(p->src.c_string) , k ) ;
- p->c_ptr = (long)CurrentString ;
- p->c_len = k ;
- }
- else
- {
- bcopy( CurrentInputFile , &(p->src.c_file) , sizeof(struct InputFile) ) ;
- if (! (CurrentInputFile->if_Flag & IFF_LOADED))
- {
- bcopy( CurrentInputFile->if_Buf , p->c_ibuf , CurrentInputFile->if_BufLen ) ;
- p->c_seek = lseek( p->src.c_file.if_Desc , 0 , 1 ) ;
- if ( p->c_seek == -1 ) Fatal( ERR_SEEK ) ;
- }
- p->c_ptr = (long)CurrentInputFile ;
- }
-
- bcopy( OutputBuf , p->c_obuf , OutputLen ) ;
- p->c_olen = OutputLen ;
- p->c_imod = InputMode ;
- p->c_flag = Flg ;
-
- if ( indic )
- {
- if ( LastContext ) free( LastContext ) ;
- LastContext = p ;
- }
- else Push( TE_CONTEXT , p ) ;
- }
-
- /**************************************************************************/
-
- void RestoreContexte( indic )
- long indic ;
-
- {
- register struct Contexte *p ;
-
- if ( indic ) p = LastContext ;
- else p = (struct Contexte *) Pop( TE_CONTEXT , 1 ) ;
-
- Flg = p->c_flag ;
- InputMode = p->c_imod ;
- if ( InputMode & IM_EXMACRO )
- {
- CurrentMacro = (struct Macro *)p->c_ptr ;
- bcopy( &(p->src.c_macro) , CurrentMacro , p->c_len ) ;
- }
- else if ( InputMode & IM_STRING )
- {
- CurrentString = (struct String *)p->c_ptr ;
- bcopy( &(p->src.c_string) , CurrentString , p->c_len ) ;
- }
- else
- {
- CurrentInputFile = (struct InputFile *)p->c_ptr ;
- bcopy( &(p->src.c_file) , CurrentInputFile, sizeof(struct InputFile) ) ;
- if (! (CurrentInputFile->if_Flag & IFF_LOADED))
- {
- bcopy( p->c_ibuf , CurrentInputFile->if_Buf , CurrentInputFile->if_BufLen ) ;
- if ( lseek( p->src.c_file.if_Desc , p->c_seek , 0 ) == -1 )
- Fatal( ERR_SEEK ) ;
- }
- }
-
- bcopy( p->c_obuf , OutputBuf , OutputLen ) ;
- OutputLen = p->c_olen ;
- free( p ) ;
- if ( indic ) LastContext = NULL ;
- }
-
- /**************************************************************************/
-
- void NewString( str )
- char *str ;
-
- {
- register struct String *s ;
-
- if ( ! *str ) return ;
-
- if ( InputMode & IM_STRING ) Push( TE_STRING , CurrentString ) ;
- if ( InputMode & IM_EXMACRO ) Push( TE_MACRO , CurrentMacro ) ;
- Push( TE_INMODE , InputMode ) ;
- BCLR( InputMode , (IM_STRING|IM_EXMACRO) ) ;
-
- s = (struct String *)myalloc( sizeof(struct String) , 0 ) ;
- strcpy( s->s_val , str ) ;
- s->s_len = strlen( str ) ;
- s->s_pos = 0 ;
- CurrentString = s ;
- BSET( InputMode , IM_STRING ) ;
- }
-
- /**************************************************************************/
-
- unsigned char *TestString( p )
- register unsigned char *p ;
-
- {
- unsigned char *s, *d ;
-
- p++ ;
- if (! *p) Fatal( ERR_SYNTAX ) ;
- s = p ;
- while ( (*p != '\'') && (*p != '\0') ) p++ ;
- if ( *p != '\'' ) Fatal( ERR_SYNTAX ) ;
- *p = '\0' ;
-
- p++ ;
- if (! *p) Fatal( ERR_SYNTAX ) ;
- d = p ;
- while ( (*p != '\'') && (*p != '\0') ) p++ ;
- if ( *p != '\'' ) Fatal( ERR_SYNTAX ) ;
- *p = '\0' ;
-
- p++ ;
- if ( strcmp( s , d ) ) BSET( Flg , F_WASFALSE ) ;
- return( p ) ;
- }
-
- /**************************************************************************/
-
- unsigned char *TestNum( p )
- unsigned char *p ;
-
- {
- register char c ;
- register long s , d ;
-
- s = strtol( p , &p , 10 ) ;
- while ( isspace(*p) ) p++ ;
-
- if (! *p) Fatal( ERR_SYNTAX ) ;
- c = *p ;
- p++ ;
- while ( isspace(*p) ) p++ ;
-
- if (! *p) Fatal( ERR_SYNTAX ) ;
- d = strtol( p , &p , 10 ) ;
-
- switch ( c )
- {
- case '<' : if ( s >= d ) BSET( Flg , F_WASFALSE ) ; break ;
- case '>' : if ( s <= d ) BSET( Flg , F_WASFALSE ) ; break ;
- case '=' : if ( s != d ) BSET( Flg , F_WASFALSE ) ; break ;
- default : Fatal( ERR_SYNTAX ) ;
- }
-
- return( p ) ;
- }
-