package xdc.rta;

import java.io.IOException;
import xdc.rov.ISymbolTable;

/*
 *  ======== Formatter ========
 *  Class for formatting printf strings.
 *  
 *  This class intended to be used for decoding printfs from xdc.runtime.Log
 *  records. An important assumption is that all of the printf arguments have
 *  been cast to IArgs on the target. 
 *  
 *  For targets with 32-bit IArgs but 16-bit integers, for example, this means
 *  that the 16-bit values must be cast to 32-bits (handling sign extension)
 *  before passing them to the Formatter.
 */
public class Formatter {

    private static ISymbolTable symTab = null;
    private static IOFReader ofReader = null;
    private static int argSize = 32;
    
    public static void setSymbolTable(ISymbolTable inSymTab)
    {
        symTab = inSymTab;
    }
	
    public static void setOFReader(IOFReader inOFReader)
    {
        ofReader = inOFReader;
    }

    /*
     *  ======== setArgSize ========
     *  Set the size of the target Arg type in bits.
     *
     *  This is used when looking up strings on the target. The arguments
     *  are assumed to be signed values, which need to be converted to 
     *  unsigned in order to treat them as addresses.
     */
    public static void setArgSize(int inArgSize)
    {
        argSize = inArgSize;
    }
    
    public static ISymbolTable getSymbolTable()
    {
        return (symTab);
    }
    
    /*
     *  ======== ParseData ========
     */
    static class ParseData {
        /* The string to be added to the result. */
        public String str;

        /* 
         * The number of characters of the string to use. 
         * Maintaining this number minimizes the amount of string
         * manipulation that needs to be done--instead of removing
         * characters from 'str', less characters are added to the
         * result.
         */
        public int len;
        public boolean lJust;
        public boolean lFlag;
        public int zpad;
        public int width;
        public int precis;
    }
    
    /*
     *  ======== doPrint ========
     *  Performs printf style formatting.
     *  
     *  This API does not require the argument size, it assumes a default
     *  size of 4.
     */
    public static String doPrint(String format, int [] args)
    {
        return (doPrintRecur(format, args, 4).result);
    }
    
    /*
     *  ======== doPrint ========
     *  Peforms printf style formatting.
     *  
     *  This API requires the argument size.
     */
    public static String doPrint(String format, int [] args, int argSize)
    {
        return (doPrintRecur(format, args, argSize).result);
    }
    
    /*
     *  ======== Result ========
     *  Structure to hold the result of a recursive doPrint, including
     *  the formatted string and the number of arguments consumed.
     */
    public static class Result {
       String result = "";
       int numArgsConsumed = 0;
    }
    
    /*
     *  ======== doPrintRecur ========
     *  Perform printf formatting with support for recursive format strings
     *  
     *  format  - The string to be formatted
     *  args    - Array of arguments to the format string
     *  argSize - The size of the target type 'Arg' in bytes. This is used to
     *            determine the number of digits to use when converting an arg
     *            to its hexadecimal representation, as well as for correctly
     *            upcasting the arguments to 64-bit longs (handling sign 
     *            extension). The arguments must be upcast to 64-bit longs 
     *            because there is no unsigned int type in Java.
     *  
     *  The return value includes the formatted string and the number of 
     *  arguments consumed by this call to doPrint. This supports recursive
     *  formatting for the %$S specifier.
     */    
    private static Result doPrintRecur(String format, int [] args, int argSize) 
    {
        Result res = new Result();
        
        /* Check for null format string */
        if (format == null) {
            res.result = "(null format)"; 
            return (res);
        }
                
        /* 
         * Convert the format string to a char array so we can treat it one
         * character at a time. 
         */
        char [] fmt = format.toCharArray();

        /* The current character we're looking at. */
        char c;
        
        /* Running index into format string */
        int findex = 0;     
        
        /* Running index into args array */
        int aindex = 0;     
        
        /* Data structure to hold meta data for a single format specifier. */
        ParseData parse = new ParseData();
        
        /* 
         * Look at each character in the string.
         * 
         * When a format specifier is encountered, this code will deal with all
         * of the characters in the specifier before doing another iteration of
         * the while loop.  
         */
        while (findex < fmt.length) {
            
            /* Look at the next character. */
            c = fmt[findex++];
            
            /* 
             * If it's not a format specifier, just add it to the result
             * and move on to the next character.
             */
            if (c != '%') {
                res.result += Character.toString(c);
                continue;
            }

            /*
             * We've found a format specifier. Get the next character in the
             * specifier.  
             */
            c = fmt[findex++];
            
            /* check for - flag (pad on right) */
            if (c == '-') {
                parse.lJust = true;
                c = fmt[findex++];
            }
            else {
                parse.lJust = false;
            }

            /* check for leading 0 pad */
            if (c == '0') {
                parse.zpad = 1;
                c = fmt[findex++];
            }
            else {
                parse.zpad = 0;
            }

            /* allow optional field width/precision specification */
            parse.width = 0;
            parse.precis = -1;

            if (c == '*') {
                parse.width = aindex >= args.length ? 0 : args[aindex++];
                c = fmt[findex++];
                if (parse.width < 0) {
                    parse.lJust = true;
                    parse.width = -parse.width;
                }
            }
            else {
                while (c >= '0' && c <= '9') {
                    parse.width = parse.width * 10 + c - '0';
                    c = fmt[findex++];
                }
            }

            /* allow optional field precision specification */
            if (c == '.') {
                parse.precis = 0;
                c = fmt[findex++];
                if (c == '*') {
                    parse.precis = aindex >= args.length ? 0 : args[aindex++];
                    if (parse.precis < 0) {
                        parse.precis = 0;
                    }
                    
                    c = fmt[findex++];
                }
                else {
                    while (c >= '0' && c <= '9') {
                        parse.precis = parse.precis * 10 + c - '0';
                        c = fmt[findex++];
                    }
                }
            }

            /* setup for leading zero padding */
            if (parse.zpad != 0) {
                parse.zpad = parse.width;
            }

            if (parse.precis > parse.zpad) {
                parse.zpad = parse.precis;
            }

            /* check for presence of l flag (e.g., %ld) */
            if (c == 'l' || c == 'L') {
                parse.lFlag = true;
                c = fmt[findex++];
            }
            else {
                parse.lFlag = false;
            }

            parse.str = "";
            parse.len = 0;

            int val = aindex >= args.length ? 0 : args[aindex++];

            if (c == 'd' || c == 'i') {
                /* signed decimal */
                parse.str = formatNum(val, parse.zpad, -10, argSize);
                parse.len = parse.str.length();
            }
            else if (c == 'u' ||       /* unsigned decimal */
                     c == 'x' ||       /* unsigned hex */
                     c == 'X' ||       /* uppercase hex */
                     c == 'o') {       /* unsigned octal */
                int base = 10;
                if (c == 'x' || c == 'X') {
                    base = 16;
                }
                else if (c == 'o') {
                    base = 8;
                }
                
                if (c == 'X') {
                    /* Parse using upper case digits */
                    parse.str = formatNum(val, parse.zpad, base, argSize, true);
                }
                else {
                    /* Parse using lower case digits */
                    parse.str = formatNum(val, parse.zpad, base, argSize, false);
                }
                
                parse.len = parse.str.length();
            }
            else if (c == 'p') {
                parse.zpad = 2 * argSize;
                parse.str = formatNum(
                    val,
                    parse.zpad, 16,
                    argSize);
                parse.str = "@" + parse.str;
                parse.len = parse.str.length();
            }
            else if (c == 'c') {
                /* character */
                parse.str = Character.toString((char)val);
                parse.len = 1;
            }
            else if (c == 'r') {
                /* lookup symbol table symbol */
                parse.str = lookupSymbol(val);
                parse.len = parse.str.length();
            }
            else if (c == 's') {
                /* string */
                /* substitute (null) for NULL pointer */
                if (val == 0) {
                    parse.str = "(null)";
                }
                else {
                    parse.str = lookupString(val);
                }
                parse.len = parse.str.length();

                if (parse.precis != -1 && parse.precis < parse.len) {
                    parse.len = parse.precis;
                }
            }
            /* Check for extended format types */
            else if (c == '$') {
                c = fmt[findex++];
                
                /* Call site, displayed as a file and line number. */
                if (c == 'F') {

                    /* The next argument should contain the line number. */
                    int lineNum = args[aindex++];
                    String fileName = (val == 0)
                        ? "(unknown file)" : lookupString(val);

                    /* 
                     * In respecting the maximum length, we don't want to print
                     * partial file names or line numbers.
                     */
                    if (parse.precis != -1) {
                        /* Retrieve the file name string */
                        parse.str = "\"" + fileName + "\"";    
                        
                        parse.len = parse.str.length();
                        
                        /* If the file name is too long, drop it. */
                        if (parse.len > parse.precis) {
                            parse.len = 0;
                        }
                        else {
                            String line = ", line " + lineNum + ": ";
                            /* If the line number fits, add it. */
                            if ((parse.len + line.length()) <= parse.precis) {
                                parse.str += line;
                                parse.len = parse.str.length();
                            }
                        }
                    }
                    /*
                     * If no precision (maximum length) is specified, just
                     * create and return the string
                     */
                    else {
                        parse.str = "\"" + fileName + "\"" +
                                    ", line " + lineNum + ": ";
                        parse.len = parse.str.length();
                    }
                }
                /* Recursive format string. */
                else if (c == 'S') {
                    /* Retrieve the format string. */
                    String recurFmt = lookupString(val);
                    
                    /* Create a new array to store the rest of the args. */
                    int[] recurArgs = new int[args.length - aindex];

                    /* Copy the remaining args into the new array. */
                    System.arraycopy(args, aindex, recurArgs, 0, recurArgs.length);
                    
                    /* Perform a recursive format */
                    Result temp = doPrintRecur(recurFmt, recurArgs, argSize);

                    /* Store the formatted string in the parse object. */
                    parse.str = temp.result;
                    parse.len = parse.str.length();
                    
                    /* 
                     * Update the arg index based on the number of arguments 
                     * consumed by the recursive call. 
                     */
                    aindex += temp.numArgsConsumed;
                }
            }
            else {
                /* unknown format, just output the character */
                parse.str = Character.toString(c);
                parse.len = 1;
                aindex--; /* unget the value */
            }

            /* compute number of characters left in field */
            parse.width -= parse.len;

            if (!parse.lJust) {
                /* pad with blanks on left */
                while (--parse.width >= 0) {
                    res.result += " ";
                }
            }

            /* 
             * Output number, character or string. Only output as many 
             * characters as parse.len. 
             */
            res.result += parse.str.substring(0, parse.len);

            /* pad with blanks on right */
            if (parse.lJust) {
                while (--parse.width >= 0) {
                    res.result += " ";
                }
            }
                        
        } /* while */
    
        /* 
         * Return the number of arguments consumed through the 
         * 'numArgsConsumed' parameter.
         */
        res.numArgsConsumed = aindex; 
        
        /* Return the formatted string. */
        return (res);
    }

    /*
     *  ======== formatNum ========
     */
    static String formatNum(int val, int zpad, int base, int argSize)
    {
    	return (formatNum(val, zpad, base, argSize, false));
    }
    
    /*
     *  ======== formatNum ========
     *  Converts 'val' into a string.
     *  
     *  The 'argSize' is used here to correctly upcast the 'val' to a 64-bit
     *  long, while handling sign extension.
     *  
     *  'base' is, e.g, -10, 10, 16
     */
    static String formatNum(int val, int zpad, int base, int argSize, boolean caps)
    {
        String res = "";
        int i = 0;
        char sign = '\0';       
        
        char[] upper = {
	        '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
	        'A', 'B', 'C', 'D', 'E', 'F'
	    };
        
        char[] lower = {
	        '0', '1', '2', '3', '4', '5', '6', '7', '8', '9',
	        'a', 'b', 'c', 'd', 'e', 'f'
	    };
        
        char [] digtohex;
        
        if (caps) {
	        digtohex = upper;
        }
        else {
        	digtohex = lower;
        }
            
        long n;
        
        /* If 'val' is positive, we can simply cast it. */
        if (val >= 0) {
        	n = val;
        }
        /* 
         * Otherwise, if val is negative and the type is signed,
         * we can just cast it. We remove the sign for conversion purposes
         * (the value will be used to index into an array), and account for
         * it separately.
         */
        else if (base < 0) {
            n = -val;
            /* account for sign '-': ok since zpad is signed */
            --zpad;
            sign = '-';        	
        }
        /* 
         * Otherwise, if val is negative and the type is unsigned, we 
         * need to strip the sign bits from the value after casting it.
         * Casting it will sign-extend the value, which is incorrect, so
         * we must remove the sign extension bits.
         */
        else {
            n = val;
            n += (0x1L << (8 * argSize));
        }
        
        /* 
         * Remove the negative sign from 'base' (the base value will
         * be used in calculating an index to an array).
         */
        if (base < 0) {
            base = -base;
        }
    
        /* Compute digits in the number from right to left. */
        do {
            res = digtohex[(int)(n % base)] + res;
            n = n / base;
            ++i;
        } while (n != 0);
    
        /* pad with leading 0s on left */
        while (i < zpad) {
            res = '0' + res;
            ++i;
        }
    
        /* add sign indicator */
        if (sign != '\0') {
            res = sign + res;
        }

        return (res);
    }

    /*
     *  ======== lookupString ========
     */
    private static String lookupString(long addr)
    {
        /* 
         * Convert address to unsigned.
         * The arguments are signed IArgs, so the address may be negative and
         * need to be converted.
         */
        if (addr < 0) {
            addr += Math.pow(2, argSize);    
        }
        
        if (ofReader != null) {
            String str = ofReader.findString(addr);
            if (str != null) {
                return (str);
            }
        }

        /* can't find a static string */
        return ("<String @" + Long.toHexString(addr) + ">");
    }
    
    /*
     *  ======== lookupSymbol ========
     *  Lookup symbol name in symbol table
     */
    private static String lookupSymbol(long addr)
    {
        /* 
         * Convert address to unsigned.
         * The arguments are signed IArgs, so the address may be negative and
         * need to be converted.
         */
        if (addr < 0) {
            addr += Math.pow(2, 32);    
        }
        
        if (symTab != null) {
            String symbols[] = null;
            /* Try code symbol first. */
            symbols = symTab.lookupFuncName(addr);
            if ((symbols != null) && (symbols.length > 0)) {
                return (symbols[0]);
            }
            
            /* If no code symbol, try data symbol. */
            symbols = symTab.lookupDataSymbol(addr);
            if ((symbols != null) && (symbols.length > 0)) {
                return (symbols[0]);
            }
        }

        /* can't find symbol name */
        return ("<Symbol @" + Long.toHexString(addr) + ">");	
    }

    
    /* This dummy class is used to help test the format code. */
    public class TestOFReader implements xdc.rta.IOFReader
    {
        public static final int FILE_NAME = 1;
        public static final int FORMAT_STRING = 2;

        
        /* Parse and close are unused. */
        public String parse(String fileName) throws IOException {
            return null;
        }
        public void close() throws IOException {
        }

        /* 
         *  ======== findString ========
         *  This implementation returns hardcoded strings
         */
        public String findString(long addr) {
            switch ((int) addr) {
                case FILE_NAME:
                    return ("MyCode.c");
                case FORMAT_STRING:
                    return ("Test format str %d %d %d");
                default:
                    return ("Bad string value!");
            }
        }
    }

    /*
     *  ======== main ========
     *  Simple unit test of doPrint
     */
    static public void main(String [] args)
    {
        String [] fmts = {
            "%%d test: %0.3d, %.3d, %3d, '%-3d', '%-0.3d'\n",
            "%%x test: %0.3x, %.3x, %3x, '%-3x', '%-0.3x'\n",
            "%%X test: %0.3X, %.3X, %3X, '%-3X', '%-0.3X'\n",
            "%%o test: %0.3o, %.3o, %3o, '%-3o', '%-0.3o'\n",
            "%%p test: %0.3p, %.3p, %3p, '%-3p', '%-0.3p'\n",
            "%%u test: %0.3u, %.3u, %3u, '%-3u', '%-0.3u'\n",
            "too many %%'s test: %x, %x, %x, %x, %x, %x, %x\n",
            "%%* test: '%0.*d', '%*.*d'\n",
        };
        
        int [] argv = {1, 2, 3, 4, 5};
        for (int i = 0; i < fmts.length; i++) {
            System.out.print(doPrint(fmts[i], argv));
            System.out.print(doPrint(fmts[i], argv, 2));
        }

        argv = new int [] {-1, -2, -3, -4, -5};
        for (int i = 0; i < fmts.length; i++) {
            System.out.print(doPrint(fmts[i], argv));
            System.out.print(doPrint(fmts[i], argv, 2));
        }

        System.out.print(doPrint(
            "%%*x test: '%0.*x', '%*.*x', '%*.*x'\n",
            new int [] {5, 0xcafe,
                        -7, 0, 0xbeef,
                        7, 0, 0xbabe}, 2));

        System.out.print(doPrint(
            "%%*x test: '%0.*x', '%*.*x', '%*.*x'\n",
            new int [] {5, 0xcafe,
                        -7, 0, 0xbeef,
                        7, 0, 0xbabe}, 4));

        System.out.print(doPrint(
            "%%s test: '%*s', '%s'\n",
            new int [] {10, 0, 17}, 4));

        System.out.print(doPrint(
            "%%r test: '%*r', '%r'\n",
            new int [] {5, 0, 17}, 4));
     
        /* Test out the %$S and %$F format specifiers. */        
        TestOFReader testOFReader = (new Formatter()).new TestOFReader();
        Formatter.setOFReader(testOFReader);
                
        System.out.print(doPrint("Recursive message: %$S, additional arg: %d\n", 
                                new int[] {TestOFReader.FORMAT_STRING, 1, 2, 3, 4}));
        
        System.out.print(doPrint("%$F%$S\n",
                                 new int [] {TestOFReader.FILE_NAME, 124, 
                                             TestOFReader.FORMAT_STRING, 1, 2, 3}));
    }
}
