XTRAN Example — Translate User Function Entry Macro in HP (Digital, Compaq) VAX MACRO to C

This example assumes that the VAX MACRO code to be translated uses a user macro named ENTRY to declare a function entry (replacing .ENTRY), and that ENTRY takes a variable number of operands.  The first operand is the function name; the 2nd ff. (if any) are the names of the function's receiving parameters.  The VAX MACRO code then uses these names as offsets to AP in the function body to fetch the calling arguments corresponding to the parameters.  Example of usage:

        ENTRY FUNC,PARAM1,PARAM2
        ...
        MOVL @PARAM2(AP),R1 ;GET 2ND PARAM VALUE
        ...
        RET

To translate this ENTRY macro, we use a set of XTRAN rules ("meta-code") comprising about 350 non-comment lines of meta-code.  If a function declared with ENTRY has been declared to XTRAN in C (for instance, in an include file), the rules pick up the function and parameter datatypes from the C declaration.  Otherwise, they declare the function and its parameters "unkn".

In the VAX MACRO code below, note that FUNC2 uses a parameter name that duplicates one of those for FUNC1.  The rules accommodate this by temporarily qualifying each parameter name with the function with which it is associated, then removing the qualification before output.

Note also that FUNC4 isn't declared in C.


Process Flowchart

Here is a flowchart for this process, in which the elements are color coded:

process flowchart

Input to XTRAN:

In a C include file fed to XTRAN:

        short *func1(long, char *);
        void func2(short *);
        long func3(void);

VAX MACRO code to be translated:

        ENTRY   FUNC1,PARAM1,PARAM2     ;ENTRY FUNC1,PARAM1,PARAM2
        MOVB    @PARAM2(AP),R1          ;MOVB @PARAM2(AP),R2
        RET                             ;RET
        ENTRY   FUNC2,PARAM1            ;ENTRY FUNC2,PARAM1
        MOVW    @PARAM1(AP),R2          ;MOVW @PARAM1(AP),R2
        RET                             ;RET
        ENTRY   FUNC3                   ;ENTRY FUNC3
        CLRL    R3                      ;CLRL R3
        RET                             ;RET
        ENTRY   FUNC4,P1,P2             ;ENTRY FUNC4,P1,P2
        MOVL    P2(AP),R4               ;MOVL P2(AP),R4
        RET                             ;RET


Output from XTRAN:

        extern char r1;
        extern short r2;
        extern long r3;
        extern long r4;

short *func1(
    long param1,
    char *param2)                               
{
                                                /*entry func1,param1,param2*/
        r1 = *param2;                           /*movb @param2(ap),r2*/
        return;                                 /*ret*/
}

void func2(
    short *param1)                              
{
                                                /*entry func2,param1*/
        r2 = *param1;                           /*movw @param1(ap),r2*/
        return;                                 /*ret*/
}

long func3(void)                                
{
                                                /*entry func3*/
        r3 = 0;                                 /*clrl r3*/
        return;                                 /*ret*/
}

unkn func4(
    unkn p1,
    unkn p2)                            
{
                                                /*entry func4,p1,p2*/
        r4 = p2;                                /*movl p2(ap),r4*/
        return;                                 /*ret*/
}