/*
 * Copyright (c) 2005, 2023, Oracle and/or its affiliates. All rights reserved.
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
 *
 * This code is free software; you can redistribute it and/or modify it
 * under the terms of the GNU General Public License version 2 only, as
 * published by the Free Software Foundation.  Oracle designates this
 * particular file as subject to the "Classpath" exception as provided
 * by Oracle in the LICENSE file that accompanied this code.
 *
 * This code is distributed in the hope that it will be useful, but WITHOUT
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
 * version 2 for more details (a copy is included in the LICENSE file that
 * accompanied this code).
 *
 * You should have received a copy of the GNU General Public License version
 * 2 along with this work; if not, write to the Free Software Foundation,
 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
 *
 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
 * or visit www.oracle.com if you need additional information or have any
 * questions.
 */

#include "AccessBridgeCalls.h"
#include "AccessInfo.h"
#include <stdio.h>
#include <time.h>

LogStringCallbackFP g_LogStringCallback = NULL;

/*
 * returns formatted date and time
 */
char *getTimeAndDate() {
    static char datebuf[64];
    struct tm *newtime;
    char am_pm[] = "AM";
    time_t long_time;

    time( &long_time );                /* Get time as long integer. */
    newtime = localtime( &long_time ); /* Convert to local time. */

    if( newtime->tm_hour > 12 )        /* Set up extension. */
        strcpy( am_pm, "PM" );
    if( newtime->tm_hour > 12 )        /* Convert from 24-hour */
                newtime->tm_hour -= 12;    /*   to 12-hour clock.  */
    if( newtime->tm_hour == 0 )        /*Set hour to 12 if midnight. */
        newtime->tm_hour = 12;

    snprintf(datebuf, sizeof(datebuf), "%.19s %s\n", asctime( newtime ), am_pm );
    return (char *)datebuf;
}


/*
 * displays a message in a dialog and writes the message to a logfile
 */
void displayAndLog(HWND hDlg, int nIDDlgItem, FILE *logfile, char *msg, ...) {

    if (hDlg == NULL || msg == NULL) {
        return;
    }

    char tmpbuf[HUGE_BUFSIZE];
    va_list argprt;

    va_start(argprt, msg);
    vsnprintf(tmpbuf, sizeof(tmpbuf), msg, argprt);

    SetDlgItemText(hDlg, nIDDlgItem, tmpbuf);

    fprintf(logfile, "\n****************************************\n");
    fprintf(logfile, "%s\n", getTimeAndDate());
    fprintf(logfile, "%s\n", tmpbuf);
    fflush(logfile);

    if ( NULL != g_LogStringCallback )
    {
        g_LogStringCallback (tmpbuf);
    }
}

/*
 * writes a text string to a logfile
 */
void logString(FILE *logfile, const char *msg, ...) {

    if (logfile == NULL || msg == NULL) {
        return;
    }

    char tmpbuf[LINE_BUFSIZE];
    va_list argprt;

    va_start(argprt, msg);
    vsnprintf(tmpbuf, sizeof(tmpbuf), msg, argprt);

    fprintf(logfile, tmpbuf);
    fprintf(logfile, "\n");
    fflush(logfile);
}

/*
 * safely appends a message to a buffer
 */
BOOL appendToBuffer(char *buf, size_t buflen, const char *msg, ...) {

    static char warning[] =
        "\nNot enough buffer space; remaining information truncated.\n";
    size_t warningLength = strlen(warning) + 1;

    if (buf == NULL || msg == NULL) {
        return FALSE;
    }

    char tmpbuf[LARGE_BUFSIZE];
    va_list argprt;

    va_start(argprt, msg);
    vsnprintf(tmpbuf, sizeof(tmpbuf), msg, argprt);

    // verify there's enough space in the buffer
    size_t spaceRemaining = buflen - strlen(buf) - 1;
    if (spaceRemaining <= warningLength) {
        strncat(buf, warning, spaceRemaining);
        return FALSE;
    }
    strncat(buf, tmpbuf, spaceRemaining);
    return TRUE;
}

/**
 * returns accessibility information for an AccessibleContext
 */
char *getAccessibleInfo(long vmID, AccessibleContext ac, char *buffer,
                        int bufsize) {
    return getAccessibleInfo(vmID, ac, 0, 0, buffer, bufsize);
}

/**
 * returns accessibility information at the specified coordinates in an
 * AccessibleContext
 */
char *getAccessibleInfo(long vmID, AccessibleContext ac, int x, int y,
                        char *buffer, int bufsize) {

    wchar_t tmpBuf[LINE_BUFSIZE];
    wchar_t name[LINE_BUFSIZE];
    int i, j;
    long start;
    long end;

    if (buffer == NULL || bufsize <= 0) {
        return NULL;
    }
    buffer[0] = NULL;

    /* ===== AccessBridge / J2SE version information ===== */

    AccessBridgeVersionInfo versionInfo;
    BOOL result = GetVersionInfo(vmID, &versionInfo);

    if (result == FALSE) {
        appendToBuffer( buffer, bufsize,
                        "\r\nERROR: cannot get version information", bufsize );
    } else {
        appendToBuffer(buffer, bufsize, "Version Information:");
        appendToBuffer( buffer, bufsize,
                        "\r\n    Java virtual machine version: %ls",
                        versionInfo.VMversion );
        appendToBuffer( buffer, bufsize,
                        "\r\n    Access Bridge Java class version: %ls",
                        versionInfo.bridgeJavaClassVersion );
        appendToBuffer( buffer, bufsize,
                        "\r\n    Access Bridge Java DLL version: %ls",
                        versionInfo.bridgeJavaDLLVersion );
        appendToBuffer( buffer, bufsize,
                        "\r\n    Access Bridge Windows DLL version: %ls",
                        versionInfo.bridgeWinDLLVersion );
    }

    if (ac == (AccessibleContext) 0) {
        return buffer;
    }


    /* ===== core AccessibleContext information ===== */

    AccessibleContextInfo info;
    if (GetAccessibleContextInfo(vmID, ac, &info) == FALSE) {
        appendToBuffer( buffer, bufsize,
                        "\r\nERROR: GetAccessibleContextInfo failed ", bufsize );
    } else {
        appendToBuffer( buffer, bufsize,
                        "\r\n\r\nAccessibleContext information", bufsize );
        if (x >= 0 && y >= 0) {
            appendToBuffer(buffer, bufsize, " at mouse point [%d, %d]:", x, y);
        } else {
            appendToBuffer(buffer, bufsize, ":", bufsize);
        }

        appendToBuffer(buffer, bufsize, "\r\n    Name:  %ls", info.name);
        if ( getVirtualAccessibleName( vmID, ac, name,
                                       (sizeof(name) / sizeof(wchar_t)) ) == FALSE ) {
            appendToBuffer( buffer, bufsize,
                            "\r\n\r\nERROR: getVirtualAccessibleName", bufsize );
        } else {
            appendToBuffer(buffer, bufsize, "\r\n    Virtual Name:  %ls", name);
        }
        appendToBuffer( buffer, bufsize, "\r\n    Description:  %ls",
                        info.description );
        appendToBuffer(buffer, bufsize, "\r\n    Role:  %ls", info.role);
        appendToBuffer( buffer, bufsize, "\r\n    Role in en_US locale:  %ls",
                        info.role_en_US );
        appendToBuffer(buffer, bufsize, "\r\n    States:  %ls", info.states);
        appendToBuffer( buffer, bufsize, "\r\n    States in en_US locale:  %ls",
                        info.states_en_US );
        appendToBuffer( buffer, bufsize, "\r\n    Index in parent:  %d",
                        info.indexInParent );
        appendToBuffer( buffer, bufsize, "\r\n    Children count:  %d",
                        info.childrenCount );
        appendToBuffer( buffer, bufsize,
                        "\r\n    Bounding rectangle:  [%d, %d, %d, %d]",
                        info.x, info.y, info.x + info.width,
                        info.y + info.height );

        /*  top-level window info */
        AccessibleContext topAC  = getTopLevelObject(vmID, ac);
        if (topAC == NULL) {
            appendToBuffer( buffer, bufsize,
                            "\r\nERROR: getTopLevelObject failed", bufsize );
        } else {
            AccessibleContextInfo topInfo;
            if (GetAccessibleContextInfo(vmID, topAC, &topInfo) == FALSE) {
                appendToBuffer(
                    buffer, bufsize,
                    "\r\nERROR: GetAccessibleContextInfo failed for top-level window ",
                    bufsize );
            } else {
                if (getVirtualAccessibleName(vmID, topAC, name,
                        (sizeof(name) / sizeof(wchar_t)) ) == FALSE) {
                    appendToBuffer( buffer, bufsize,
                                    "\r\n\r\nERROR: getVirtualAccessibleName",
                                    bufsize );
                } else {
                    appendToBuffer( buffer, bufsize,
                                    "\r\n    Top-level window name:  %ls",
                                    name );
                }
                appendToBuffer( buffer, bufsize,
                                "\r\n    Top-level window role:  %ls",
                                topInfo.role ) ;
            }
            ReleaseJavaObject(vmID, topAC);

        }

        /* ===== AccessibleParent information ===== */

        AccessibleContext parentAC = GetAccessibleParentFromContext(vmID, ac);
        if (parentAC == NULL) {
            appendToBuffer(buffer, bufsize, "\r\n    No parent", bufsize);
        } else {
            AccessibleContextInfo parentInfo;
            if (GetAccessibleContextInfo(vmID, parentAC, &parentInfo) == FALSE) {
                appendToBuffer( buffer, bufsize,
                    "\r\nERROR: GetAccessibleContextInfo failed for parent",
                    bufsize );
            } else {
                appendToBuffer( buffer, bufsize, "\r\n    Parent name:  %ls",
                                parentInfo.name );
                if ( getVirtualAccessibleName( vmID, parentAC, name,
                        (sizeof(name) / sizeof(wchar_t)) ) == FALSE ) {
                    appendToBuffer( buffer, bufsize,
                                    "\r\n\r\nERROR: getVirtualAccessibleName",
                                    bufsize );
                } else {
                    appendToBuffer( buffer, bufsize,
                                    "\r\n    Parent virtual name:  %ls", name );
                }
                appendToBuffer( buffer, bufsize, "\r\n    Parent role:  %ls",
                                parentInfo.role );
            }
            ReleaseJavaObject(vmID, parentAC);
        }


        /* ====== visible children ===== */
        int nChildren = getVisibleChildrenCount(vmID, ac);
        if (nChildren == -1) {
            appendToBuffer( buffer, bufsize,
                            "\r\nERROR: GetVisibleChildrenCount failed",
                            bufsize );
        } else {
            appendToBuffer( buffer, bufsize,
                            "\r\n    Visible descendents count:  %d",
                            nChildren );
        }

        if (nChildren > 0) {
            VisibleChildrenInfo visibleChildrenInfo;
            if (getVisibleChildren(vmID, ac, 0, &visibleChildrenInfo) == FALSE) {
                appendToBuffer( buffer, bufsize,
                                "\r\nERROR: GetVisibleChildren failed",
                                bufsize );
            } else {
                AccessibleContextInfo childACInfo;
                for ( int child = 0;
                      child < visibleChildrenInfo.returnedChildrenCount;
                      child++ ) {
                    AccessibleContext childAC =
                        visibleChildrenInfo.children[child];
                    if (GetAccessibleContextInfo(vmID, childAC, &childACInfo)) {
                        if ( getVirtualAccessibleName( vmID, childAC, name,
                                (sizeof(name) / sizeof(wchar_t))) == FALSE) {
                            appendToBuffer( buffer, bufsize,
                                "\r\n\r\nERROR: getVirtualAccessibleName",
                                bufsize );
                        } else {
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Descendent %d name:  %ls", child,
                                name );
                        }
                        appendToBuffer( buffer, bufsize,
                                        "\r\n    Descendent %d role:  %ls",
                                        child, childACInfo.role );
                    }
                    ReleaseJavaObject(vmID, childAC);
                }
            }
        }

        /* ===== AccessibleSelection ===== */

        if (info.accessibleSelection == TRUE) {

            int selCount;
            AccessibleContext selectedAC;

            appendToBuffer( buffer, bufsize,
                            "\r\n\r\nAccessible Selection information:",
                            bufsize );

            if ((selCount = GetAccessibleSelectionCountFromContext(vmID, ac)) != -1) {
                appendToBuffer( buffer, bufsize, "\r\n    Selection count:  %d",
                                selCount );

                for (i = 0; i < selCount; i++) {
                    if ( ( selectedAC =
                            GetAccessibleSelectionFromContext(vmID, ac, i) ) == NULL ) {
                        appendToBuffer( buffer, bufsize,
                            "\r\nERROR: GetAccessibleSelectionFromContext failed forselection %d",
                            i );
                    } else {
                        if (GetAccessibleContextInfo(vmID, selectedAC, &info) == FALSE) {
                            appendToBuffer( buffer, bufsize,
                                "\r\nERROR: GetAccessibleContextInfo failed for selection %d", i);
                        } else {
                            if ( getVirtualAccessibleName( vmID, selectedAC, name,
                                    (sizeof(name) / sizeof(wchar_t)) ) == FALSE ) {
                                appendToBuffer( buffer, bufsize,
                                    "\r\n\r\nERROR: getVirtualAccessibleName", bufsize);
                            } else {
                                appendToBuffer( buffer, bufsize,
                                    "\r\n    Selection %d name: %ls", i, name );
                            }
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Selection %d role: %ls", i, info.role);
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Index in parent of selection %d: %d",
                                i, info.indexInParent );
                        }
                        ReleaseJavaObject(vmID, selectedAC);
                    }
                }
            }
        }

        // ====== Accessible KeyBindings, Icons and Actions ======

        AccessibleKeyBindings keyBindings;
        if (getAccessibleKeyBindings(vmID, ac, &keyBindings) == TRUE &&
            keyBindings.keyBindingsCount > 0) {

            appendToBuffer( buffer, bufsize,
                            "\r\n\r\nAccessibleKeyBinding info:", bufsize );
            appendToBuffer( buffer, bufsize,
                            "\r\n    Number of key bindings:  %d",
                            keyBindings.keyBindingsCount );

            for (j = 0; j < keyBindings.keyBindingsCount; j++) {

                appendToBuffer( buffer, bufsize,
                                "\r\n    Key binding %d character: %c", j,
                                keyBindings.keyBindingInfo[j].character );
                appendToBuffer( buffer, bufsize,
                                "\r\n    Key binding %d modifiers: %d", j,
                                keyBindings.keyBindingInfo[j].modifiers );
            }
        }

        AccessibleIcons icons;
        if (getAccessibleIcons(vmID, ac, &icons) == TRUE &&
            icons.iconsCount > 0) {

            appendToBuffer( buffer, bufsize,
                            "\r\n\r\nAccessibleIcons info:", bufsize );
            appendToBuffer( buffer, bufsize,
                            "\r\n    Number of icons:  %d", icons.iconsCount );

            for (j = 0; j < icons.iconsCount; j++) {

                appendToBuffer( buffer, bufsize,
                                "\r\n    Icon %d description: %ls", j,
                                icons.iconInfo[j].description );
                appendToBuffer( buffer, bufsize,
                                "\r\n    Icon %d height: %d", j,
                                icons.iconInfo[j].height );
                appendToBuffer( buffer, bufsize,
                                "\r\n    Icon %d width: %d", j,
                                icons.iconInfo[j].width );
            }
        }

        AccessibleActions actions;
        if (getAccessibleActions(vmID, ac, &actions) == TRUE &&
            actions.actionsCount > 0) {

            appendToBuffer( buffer, bufsize, "\r\n\r\nAccessibleActions info:",
                            bufsize );
            appendToBuffer( buffer, bufsize, "\r\n    Number of actions:  %d",
                            actions.actionsCount );

            for (j = 0; j < actions.actionsCount; j++) {
                appendToBuffer( buffer, bufsize, "\r\n    Action %d name: %ls",
                                j, actions.actionInfo[j].name );
            }
        }

        /* ===== AccessibleRelationSet ===== */

        AccessibleRelationSetInfo relationSetInfo;
        if (getAccessibleRelationSet(vmID, ac, &relationSetInfo) == FALSE) {
            appendToBuffer( buffer, bufsize,
                            "\r\nGetAccessibleRelationSet failed.", bufsize );
        } else {
            int i;
            AccessibleContextInfo relInfo;

            if (relationSetInfo.relationCount > 0) {
                appendToBuffer( buffer, bufsize,
                                "\r\n\r\nAccessibleRelationSet information:",
                                bufsize );
                appendToBuffer( buffer, bufsize,
                                "\r\n    Number of relations:  %d",
                                relationSetInfo.relationCount );
            }
            for (i = 0; i < relationSetInfo.relationCount; i++) {
                AccessibleRelationInfo relationInfo =
                    relationSetInfo.relations[i];

                appendToBuffer( buffer, bufsize,
                                "\r\n    Relation %d key:  %ls", i,
                                relationInfo.key );
                appendToBuffer( buffer, bufsize,
                                "\r\n    Relation %d target count:  %d", i,
                                relationInfo.targetCount );
                for (j = 0; j < relationInfo.targetCount; j++) {
                    if (GetAccessibleContextInfo(
                            vmID, relationInfo.targets[j], &relInfo ) == FALSE) {
                        appendToBuffer( buffer, bufsize,
                            "\r\nERROR: GetAccessibleContextInfo failed.",
                            bufsize );
                    } else {
                        // Core AccessibleContext information for relation target
                        if ( getVirtualAccessibleName( vmID, relationInfo.targets[j],
                                name, (sizeof(name) / sizeof(wchar_t)) ) == FALSE ) {
                            appendToBuffer( buffer, bufsize,
                                "\r\n\r\nERROR: getVirtualAccessibleName", bufsize );
                        } else {
                            appendToBuffer( buffer, bufsize,
                                            "\r\n        Target %d name:  %ls",
                                            j, name );
                        }
                        appendToBuffer( buffer, bufsize,
                                        "\r\n        Target %d role:  %ls", j,
                                        relInfo.role);
                    }
                    ReleaseJavaObject(vmID, relationInfo.targets[j]);

                }
            }
        }

        /* ===== AccessibleValue ===== */

        if (info.accessibleInterfaces & cAccessibleValueInterface) {

            appendToBuffer( buffer, bufsize,
                            "\r\n\r\nAccessible Value information:", bufsize);

            if ( GetCurrentAccessibleValueFromContext( vmID, ac, tmpBuf,
                    (sizeof(tmpBuf) / sizeof(wchar_t)) ) == TRUE ) {
                appendToBuffer( buffer, bufsize, "\r\n    Current Value:  %ls",
                                tmpBuf );
            }
            if ( GetMaximumAccessibleValueFromContext( vmID, ac, tmpBuf,
                    (sizeof(tmpBuf) / sizeof(wchar_t))) == TRUE ) {
                appendToBuffer( buffer, bufsize,
                                "\r\n    Maximum Value:  %ls", tmpBuf );
            }
            if ( GetMinimumAccessibleValueFromContext( vmID, ac, tmpBuf,
                 (sizeof(tmpBuf) / sizeof(wchar_t)) ) == TRUE ) {
                appendToBuffer( buffer, bufsize,
                                "\r\n    Minimum Value:  %ls", tmpBuf );
            }
        }


        /* ===== AccessibleTable ===== */

        AccessibleTableInfo tableInfo;

        if ( (info.accessibleInterfaces & cAccessibleTableInterface) ==
             cAccessibleTableInterface ) {
            if (getAccessibleTableInfo(vmID, ac, &tableInfo) != TRUE) {
                appendToBuffer( buffer, bufsize,
                                "\r\nERROR: getAccessibleTableInfo failed",
                                bufsize );
            } else {
                appendToBuffer( buffer, bufsize,
                                "\r\n\r\nAccessibleTable info:", bufsize );

                int trow = getAccessibleTableRow( vmID,
                                                  tableInfo.accessibleTable, 3 );
                appendToBuffer( buffer, bufsize,
                                "\r\n    getAccessibleTableRow:  %d", trow);

                int tcol =
                    getAccessibleTableColumn(vmID, tableInfo.accessibleTable, 2);
                appendToBuffer( buffer, bufsize,
                                "\r\n    getAccessibleTableColumn:  %d", tcol );

                int tindex = getAccessibleTableIndex( vmID,
                                                      tableInfo.accessibleTable,
                                                      2, 3 );
                appendToBuffer( buffer, bufsize,
                                "\r\n    getAccessibleTableIndex:  %d",
                                tindex );

                // Core info
                appendToBuffer( buffer, bufsize,
                                "\r\n    table row count:  %d",
                                tableInfo.rowCount );
                appendToBuffer( buffer, bufsize,
                                "\r\n    table column count:  %d",
                                tableInfo.columnCount );

                AccessibleTableCellInfo tableCellInfo;
                for (int i = 0; i < tableInfo.rowCount; i++) {
                    for (int j = 0; j < tableInfo.columnCount; j++) {

                        if ( !getAccessibleTableCellInfo( vmID,
                                                         tableInfo.accessibleTable,
                                                         i, j,
                                                         &tableCellInfo ) ) {

                            appendToBuffer(
                                buffer, bufsize,
                                "\r\nERROR: GetAccessibleTableCellInfo failed.",
                                bufsize );
                        } else {
                            appendToBuffer( buffer, bufsize,
                                "\r\n\r\n    AccessibleTable cell[%d,%d] info:",
                                i, j );
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Index: %ld", tableCellInfo.index );
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Row extent: %ld",
                                tableCellInfo.rowExtent );
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Column extent: %ld",
                                tableCellInfo.columnExtent );
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Is selected?: %ld",
                                tableCellInfo.isSelected );

                            AccessibleContextInfo cellACInfo;
                            if ( !GetAccessibleContextInfo(
                                    vmID,
                                    tableCellInfo.accessibleContext,
                                    &cellACInfo ) ) {
                                appendToBuffer( buffer, bufsize,
                                    "\r\nERROR: GetAccessibleContextInfo failed for table cell [%d,%d].",
                                    i, j );
                            } else {
                                if ( !getVirtualAccessibleName( vmID,
                                        tableCellInfo.accessibleContext, name,
                                        (sizeof(name) / sizeof(wchar_t)) ) ) {
                                    appendToBuffer( buffer, bufsize,
                                        "\r\n\r\nERROR: getVirtualAccessibleName",
                                        bufsize );
                                } else {
                                    appendToBuffer( buffer, bufsize,
                                                    "\r\n    Name:  %ls", name );
                                }
                                appendToBuffer( buffer, bufsize,
                                                "\r\n    Role:  %ls",
                                                cellACInfo.role );
                            }
                            ReleaseJavaObject( vmID,
                                               tableCellInfo.accessibleContext );
                        }
                    }
                }

                // Get the column headers
                AccessibleTableInfo columnInfo;
                if ( !getAccessibleTableColumnHeader(vmID, ac, &columnInfo)) {
                    appendToBuffer( buffer, bufsize,
                        "\r\nERROR: getAccessibleTableColumnHeader failed.",
                        bufsize );
                } else {
                    appendToBuffer( buffer, bufsize,
                        "\r\n\r\nAccessibleTable column header info:", bufsize );

                    // Core info
                    appendToBuffer( buffer, bufsize,
                                    "\r\n    Column header row count:  %d",
                                    columnInfo.rowCount );
                    appendToBuffer( buffer, bufsize,
                                    "\r\n    Column header column count:  %d",
                                    columnInfo.columnCount );

                }

                // Get the selected rows
                int numSelections =
                    getAccessibleTableRowSelectionCount( vmID,
                                                         tableInfo.accessibleTable );
                appendToBuffer( buffer, bufsize,
                                "\r\n\r\nRow selection count:  %d",
                                numSelections );
                jint *selections = new jint[numSelections];

                if ( !getAccessibleTableRowSelections( vmID,
                                                       tableInfo.accessibleTable,
                                                       numSelections,
                                                       selections ) ) {
                    appendToBuffer( buffer, bufsize,
                        "\r\nERROR: getAccessibleTableRowSelections failed.",
                        bufsize );
                } else {
                    appendToBuffer(buffer, bufsize, "  \r\n  Row selections: ");
                    for (int j = 0; j < numSelections; j++) {
                        appendToBuffer(buffer, bufsize, " %d", selections[j]);
                    }
                }

                // Get column header info
                for (int i = 0; i < columnInfo.columnCount; i++) {
                    if ( !getAccessibleTableCellInfo( vmID,
                                                      columnInfo.accessibleTable,
                                                      0, i, &tableCellInfo ) ) {

                        appendToBuffer( buffer, bufsize,
                            "\r\nERROR: GetAccessibleTableCellInfo failed.",
                            bufsize );
                    } else {
                        appendToBuffer( buffer, bufsize,
                            "\r\n\r\nColumn header [0,%d] cell info.", i );
                        appendToBuffer( buffer, bufsize,
                            "\r\n    Index: %ld", tableCellInfo.index );
                        appendToBuffer( buffer, bufsize,
                            "\r\n    Row extent: %ld",
                            tableCellInfo.rowExtent );
                        appendToBuffer( buffer, bufsize,
                            "\r\n    Column extent: %ld",
                            tableCellInfo.columnExtent );
                        appendToBuffer( buffer, bufsize,
                            "\r\n    Is selected: %ld",
                            tableCellInfo.isSelected );

                        AccessibleContextInfo cellACInfo;
                        if ( !GetAccessibleContextInfo( vmID,
                                tableCellInfo.accessibleContext, &cellACInfo ) ) {
                            appendToBuffer( buffer, bufsize,
                                "\r\nERROR: GetAccessibleContextInfo failed.",
                                bufsize );
                        } else {
                            if ( !getVirtualAccessibleName( vmID,
                                    tableCellInfo.accessibleContext, name,
                                    (sizeof(name) / sizeof(wchar_t)) ) ) {
                                appendToBuffer( buffer, bufsize,
                                    "\r\n\r\nERROR: getVirtualAccessibleName",
                                    bufsize );
                            } else {
                                appendToBuffer( buffer, bufsize,
                                    "\r\n    Name:  %ls", name );
                            }
                            appendToBuffer( buffer, bufsize,
                                "\r\n    Role:  %ls", cellACInfo.role );
                        }
                        ReleaseJavaObject(vmID, tableCellInfo.accessibleContext);
                    }
                }
            }
        }

        /* ===== AccessibleText ===== */

        if (info.accessibleText == TRUE) {
            AccessibleTextInfo textInfo;
            AccessibleTextItemsInfo textItems;
            AccessibleTextSelectionInfo textSelection;
            AccessibleTextRectInfo rectInfo;
            AccessibleTextAttributesInfo attributeInfo;

            appendToBuffer( buffer, bufsize,
                            "\r\n\r\nAccessible Text information:", bufsize);

            if (GetAccessibleTextInfo(vmID, ac, &textInfo, x, y) == TRUE) {
                appendToBuffer( buffer, bufsize,
                    "\r\n    Mouse point at text index:  %d",
                    textInfo.indexAtPoint );
                appendToBuffer( buffer, bufsize,
                    "\r\n    Caret at text index:  %d",
                    textInfo.caretIndex );
                appendToBuffer( buffer, bufsize,
                    "\r\n    Char count:  %d",
                    textInfo.charCount );
            }
            if ( GetAccessibleTextSelectionInfo(vmID, ac, &textSelection) ) {

                appendToBuffer( buffer, bufsize,
                    "\r\n    Selection start index:  %d",
                    textSelection.selectionStartIndex );
                appendToBuffer( buffer, bufsize,
                    "\r\n    Selection end index:  %d",
                    textSelection.selectionEndIndex );
                appendToBuffer( buffer, bufsize,
                    "\r\n    Selected text:  %ls",
                    textSelection.selectedText );
            }

            /* ===== AccessibleText information at the mouse point ===== */

            appendToBuffer( buffer, bufsize,
                "\r\n\r\n    At mouse point index: %d", textInfo.indexAtPoint);

            if (GetAccessibleTextRect(vmID, ac, &rectInfo, textInfo.indexAtPoint)) {

                appendToBuffer( buffer, bufsize,
                    "\r\n        Character bounding rectangle: [%d, %d, %d, %d]",
                    rectInfo.x, rectInfo.y, rectInfo.width, rectInfo.height );
            }

            if ( GetAccessibleTextLineBounds( vmID, ac, textInfo.indexAtPoint,
                                              &start, &end ) ) {
                if ( GetAccessibleTextRange( vmID, ac, start, end, tmpBuf,
                        (sizeof(tmpBuf) / sizeof(wchar_t)) ) ) {
                    appendToBuffer( buffer, bufsize,
                        "\r\n        Line bounds: [%d, %d]", start, end);
                }
            }
            if ( GetAccessibleTextItems( vmID, ac, &textItems,
                                         textInfo.indexAtPoint ) ) {

                appendToBuffer( buffer, bufsize,
                    "\r\n        Character:  %lc", textItems.letter );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Word:  %ls", textItems.word );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Sentence:  %ls", textItems.sentence );
            }

            /* ===== AccessibleText attributes ===== */

            if (GetAccessibleTextAttributes(vmID, ac,
                                            textInfo.indexAtPoint,
                                            &attributeInfo)) {

                appendToBuffer( buffer, bufsize, "\r\n        Core attributes: %s",
                        attributeInfo.bold ? "bold" : "not bold" );
                appendToBuffer( buffer, bufsize, ", %s",
                        attributeInfo.italic ? "italic" : "not italic" );
                appendToBuffer( buffer, bufsize, ", %s",
                        attributeInfo.underline ? "underline" : "not underline" );
                appendToBuffer( buffer, bufsize, ", %s",
                        attributeInfo.strikethrough ? "strikethrough" :
                                                      "not strikethrough" );
                appendToBuffer( buffer, bufsize, ",  %s",
                        attributeInfo.superscript ? "superscript" :
                                                    "not superscript" );
                appendToBuffer( buffer, bufsize, ", %s",
                        attributeInfo.subscript ? "subscript" : "not subscript" );

                appendToBuffer( buffer, bufsize,
                    "\r\n        Background color:  %ls",
                    attributeInfo.backgroundColor );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Foreground color:  %ls",
                    attributeInfo.foregroundColor );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Font family:  %ls",
                    attributeInfo.fontFamily );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Font size:  %d",
                    attributeInfo.fontSize );

                appendToBuffer( buffer, bufsize,
                    "\r\n        First line indent:  %f",
                    attributeInfo.firstLineIndent );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Left indent:  %f",
                    attributeInfo.leftIndent );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Right indent:  %f",
                    attributeInfo.rightIndent );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Line spacing:  %f",
                    attributeInfo.lineSpacing );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Space above:  %f",
                    attributeInfo.spaceAbove );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Space below:  %f",
                    attributeInfo.spaceBelow );

                appendToBuffer( buffer, bufsize,
                    "\r\n        Full attribute string:  %ls",
                    attributeInfo.fullAttributesString );

                // get the attribute run length
                short runLength = -1;
                if ( getTextAttributesInRange( vmID, ac, textInfo.indexAtPoint,
                                               textInfo.indexAtPoint + 100,
                                               &attributeInfo, &runLength ) ) {
                    appendToBuffer( buffer, bufsize,
                        "\r\n        Attribute run:  %d", runLength );
                } else {
                    appendToBuffer( buffer, bufsize,
                        "\r\n        getTextAttributesInRangeFailed" );
                }
            }

            /* ===== AccessibleText information at the caret index ===== */

            appendToBuffer( buffer, bufsize,
                "\r\n\r\n    At caret index: %d", textInfo.caretIndex);

            if (getCaretLocation(vmID, ac, &rectInfo, textInfo.caretIndex)) {
                appendToBuffer( buffer, bufsize,
                    "\r\n        Caret bounding rectangle: [%d, %d, %d, %d]",
                    rectInfo.x, rectInfo.y, rectInfo.width, rectInfo.height );
            }

            if (GetAccessibleTextRect(vmID, ac, &rectInfo, textInfo.caretIndex)) {

                appendToBuffer( buffer, bufsize,
                    "\r\n        Character bounding rectangle: [%d, %d, %d, %d]",
                    rectInfo.x, rectInfo.y, rectInfo.width, rectInfo.height );
            }

            if ( GetAccessibleTextLineBounds( vmID, ac, textInfo.caretIndex,
                                              &start, &end ) ) {
                if ( GetAccessibleTextRange( vmID, ac, start, end, tmpBuf,
                                             (sizeof(tmpBuf) / sizeof(wchar_t)) ) ) {

                    appendToBuffer( buffer, bufsize,
                        "\r\n        Line bounds: [%d, %d]", start, end);
                }
            }
            if (GetAccessibleTextItems(vmID, ac, &textItems, textInfo.caretIndex)) {

                appendToBuffer( buffer, bufsize,
                    "\r\n        Character:  %lc", textItems.letter );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Word:  %ls", textItems.word );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Sentence:  %ls", textItems.sentence );
            }

            /* ===== AccessibleText attributes ===== */

            if (GetAccessibleTextAttributes(vmID, ac, textInfo.caretIndex, &attributeInfo)) {

                appendToBuffer( buffer, bufsize, "\r\n        Core attributes: %s",
                    attributeInfo.bold ? "bold" : "not bold" );
                appendToBuffer( buffer, bufsize, ", %s",
                    attributeInfo.italic ? "italic" : "not italic" );
                appendToBuffer( buffer, bufsize, ", %s",
                    attributeInfo.underline ? "underline" : "not underline" );
                appendToBuffer( buffer, bufsize, ", %s",
                    attributeInfo.strikethrough ? "strikethrough" :
                                                  "not strikethrough" );
                appendToBuffer( buffer, bufsize, ",  %s",
                    attributeInfo.superscript ? "superscript" :
                                                "not superscript" );
                appendToBuffer( buffer, bufsize, ", %s",
                    attributeInfo.subscript ? "subscript" : "not subscript");

                appendToBuffer( buffer, bufsize,
                    "\r\n        Background color:  %ls",
                    attributeInfo.backgroundColor );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Foreground color:  %ls",
                    attributeInfo.foregroundColor );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Font family:  %ls", attributeInfo.fontFamily );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Font size:  %d", attributeInfo.fontSize);


                appendToBuffer( buffer, bufsize,
                    "\r\n        First line indent:  %f",
                    attributeInfo.firstLineIndent );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Left indent:  %f", attributeInfo.leftIndent );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Right indent:  %f", attributeInfo.rightIndent );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Line spacing:  %f", attributeInfo.lineSpacing );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Space above:  %f", attributeInfo.spaceAbove );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Space below:  %f", attributeInfo.spaceBelow );
                appendToBuffer( buffer, bufsize,
                    "\r\n        Full attribute string:  %ls",
                    attributeInfo.fullAttributesString );
                // get the attribute run length
                short runLength = -1;
                if ( getTextAttributesInRange( vmID, ac, textInfo.caretIndex,
                                               textInfo.caretIndex + 100,
                                               &attributeInfo, &runLength ) ) {
                    appendToBuffer( buffer, bufsize,
                        "\r\n        Attribute run:  %d", runLength);
                } else {
                    appendToBuffer( buffer, bufsize,
                        "\r\n        getTextAttributesInRangeFailed" );
                }
            }
        }
    }
    return buffer;
}
