[net.micro] pascal-->C translator

KRULWICH@C.CS.CMU.EDU (Bruce Krulwich) (09/04/86)

i am interested in translating a turbo-pascal program into C.
i'm not using any pascal-only things like procedures within
procedures, and i can deal with the turbo-specific stuff
myself, so a standard pascal to standard C would be great.
does anyone have or know of such a thing??  public domain
or net-downloadable would be best.  thanks in advance.

bruce krulwich

CMU and the Pittsburgh Magnetic Resonnance Institute.
arpa: KRULWICH@C.CS.CMU.EDU
   or KRULWICH@CMU-CS-C
bitnet: BK0A%CMCCTC@CMCCVMA
uucp: ...!UCBVAX!C.CS.CMU.EDU!KRULWICH
  or  ...!UCBVAX!CMU-CS-C.ARPA!KRULWICH

walker@hpl-opus.HP.COM (Rick Walker) (09/08/86)

Bruce,

I am interested in any responses that you get to your
request for pascal to c conversion.  I would like to 
convert the public domain "software tools" from pascal
to c.  I am including a crude program which simply substitutes
for some common keywords and operators. The source file is
pretty clear so you should be able to modify it pretty easily.

To do the job right would probably require the use of lex
and yacc to parse the pascal grammar and emit c equivalents.

good luck, 
Rick Walker

cut here --------------------------------------------------
/* Pascal to C - filter to replace Pascal punctuation and and certain key words 
with their C equivalents 

derived from a similar program (see _Byte_, February 1985) which did a C to
Pascal conversion.
   

   C form           Pascal form
   ------           -----------
    "               '
    {               BEGIN
    }               END;
    <tab>           <2 blanks>
    ()              <nothing>
    &&              AND
    ||              OR
    Comment start   {
    Comment end     }
    ==              =
    !=              <>
    =               :=
    printf          writeln
    scanf           readln
    while           WHILE
 
   Usage: p2c < infile >outfile
*/

#include "ctype.h"

#define EOF -1
#define EOS  0

main ()
{
char    c,
       *letter,
        word[100];
int     wordlnth;

    letter = word;
    wordlnth = 0;
    while ((c = getchar ()) != EOF)
    {
	if (isalpha (c))
	    letter[wordlnth++] = c;
	else
	{
	    if (wordlnth > 0)
	    {			/* word ready to check */
		letter[wordlnth] = '\0';
		wtest (word);	/* pass or replace it */
		wordlnth = 0;	/* reset index */
	    } ctest (c);	/* process following char */
	}
    }
}			/* Note: the lastword in the file will be missed if it
			   is immediately followed by EOF with no intervening
			   nonalphanumeric character. This is not a problem
			   for Pascal or C program sources.  However, a
			   general purpose word filter would have to check for
			   a non-zero wordlength after EOF is reached */

wtest (word)
char   *word;
{
char   *swapword;
    swapword = word;
    switch (word[0])
    {				/* test first letter, then rest of word */
	case 'w': 
	    if (strncmp (word, "writeln", 7) == 0)
		swapword = "printf";
	    break;
	case 'W': 
	    if (strncmp (word, "WHILE", 5) == 0)
		swapword = "while";
	    break;
	case 'r': 
	    if (strncmp (word, "readln", 6) == 0)
		swapword = "scanf";
	    break;
	case 'b': 
	    if (strncmp (word, "begin", 5) == 0)
		swapword = "{";
	    break;
	case 'B': 
	    if (strncmp (word, "BEGIN", 5) == 0)
		swapword = "{";
	    break;
	case 'E': 
	    if (strncmp (word, "END", 4) == 0)
		swapword = "}";
	    break;
	case 'e': 
	    if (strncmp (word, "end", 4) == 0)
		swapword = "}";
	    break;
	case 'A':
	    if (strncmp (word, "AND", 3) == 0)
		swapword = "&&";
	    break;
	case 'a':
	    if (strncmp (word, "and", 3) == 0)
		swapword = "&&";
	    break;
	case 'O': 
	    if (strncmp (word, "OR", 2) == 0)
		swapword = "||";
	    break;
	case 'o': 
	    if (strncmp (word, "or", 2) == 0)
		swapword = "||";
	    break;
	case 'd': 
	    if (strncmp (word, "do", 2) == 0)
		swapword = "";
	    break;
	case 'D': 
	    if (strncmp (word, "DO", 2) == 0)
		swapword = "";
	    break;
	case 'n': 
	    if (strncmp (word, "not", 3) == 0)
		swapword = "!";
	    break;
	case 't': 
	    if (strncmp (word, "then", 4) == 0)
		swapword = "";
	    break;
	default: 
	    break;		/* pass unchanged */
    } swap (swapword);
}

ctest (c)
char    c;
{
    switch (c)
    {
	case '\'': 
	    putchar ('"');
	    break;
	case '{': 
		swap ("/*");
	    break; /* fix comments */
	case '}': 
	    swap ("*/");
	    break; /* fix comments */
	case ':': 
	    swapif (':', '=', "=");
	    break; /* replace := with = */
	case '<': 
	    swapif ('<', '>', "!=");
	    break; /* replace <> with != */
	case '=': 
	    swapif ('=', ' ', "==");
	    break; /* replace = with == */	
	case '(': 
	    swapif ('(', '*', "/*");
	    break; /* fix comments */
	case '*': 
	    swapif ('*', ')', "*/");
	    break; /* fix comments */
	default: 
	    putchar (c);
	    break;
    }
}

swap (s)
char   *s;
{
    while (*s != EOS)
	putchar (*s++);
}

swapif (first, second, replacement)
char    first,
        second,
        *replacement;
{
char    c;
    if ((c = getchar ()) == second)
	swap (replacement);
    else
    {
	putchar (first);
	putchar (c);
    }
}

daford@watdragon.UUCP (Daniel Ford) (09/11/86)

I wrote a Genuine PASCAL to C "converter" (compiler!) as part of a compiler
used to automatically generate communication protocols from an extended state
machine description.  My conclusions at the end of my task was that it was
"easy" but....  The major problems if I remember correctly were in dealing with
nested routines (i.e. one routine defined inside another) and the scope of
variables with in these types of structures.  I ended up renaming things in a
uniquie systematic way and then declaring (for variables) them to be external.
Other problems arose in trying to deal with the different formats of I/O
statments.  Generally one Pascal write statment converted into one or more C
printf's.  There were other problems but mostly it was just straight text
translation.  My preference would be to use a text editor to do the job.

Daniel Ford

harris@dg_rtp.UUCP (Mark Harris) (09/18/86)

I've seen somewhere a Pascal to C translator that cost either 1 or 2 grand!!