/******************************************************************************
**                                                                        
** Source File Name = async.c  1.3                                      
**                                                                        
** Licensed Materials - Property of IBM                                   
**                                                                        
** (C) COPYRIGHT International Business Machines Corp. 1995, 1999
** All Rights Reserved.
**                                                                        
** US Government Users Restricted Rights - Use, duplication or            
** disclosure restricted by GSA ADP Schedule Contract with IBM Corp.      
**                                                                        
**                                                                        
**    PURPOSE :                                                           
** Example of executing an SQL statement asynchronously.
**
** This sample is based on the fetch.c sample.
**                                                                        
** For more information about these samples see the README file.
**
** For more information on programming in CLI see the:
**     - "Building CLI Applications" section of the Application Building Guide, and the
**     - CLI Guide and Reference.
**
** For more information on the SQL language see the SQL Reference.
**
******************************************************************************/

#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <sqlcli1.h>
#include "samputil.h"          /* Header file for CLI sample code */

/* For the Macintosh environment when generating 68K applications */
#ifdef DB268K
   /* Need to include ASLM for 68K applications */
   #include <LibraryManager.h>
#endif

#define MAX_STMT_LEN 255
/* Global Variables for user id and password.
 *  To keep samples simple, not a recommended practice.
 */
    SQLCHAR   server[SQL_MAX_DSN_LENGTH + 1];
    SQLCHAR   uid[MAX_UID_LENGTH + 1];
    SQLCHAR   pwd[MAX_PWD_LENGTH + 1];

/*--> SQLL1X61.SCRIPT */
/*******************************************************************
** main
*******************************************************************/
int
main( int argc, char * argv[] )
{
    SQLHANDLE henv, hdbc, hstmt ;
    SQLRETURN       rc;

    SQLCHAR         sqlstmt[] = "SELECT deptname, location from org where division = 'Eastern'";
    struct { SQLINTEGER ind;
             SQLCHAR  s[15];
           } deptname, location;

    SQLSMALLINT     outlen; /* For calls to SQLGetInfo() */
    SQLUINTEGER     ubuffer; /* For calls to SQLGetInfo() */
    /* Make the result from SQLGetInfo() more meaningful by mapping */
    /* the returned value to the string. */
    static char ASYNCMODE[][19] =  {  "SQL_AM_NONE", 
                                      "SQL_AM_CONNECTION", 
                                      "SQL_AM_STATEMENT" };
/*<-- */ 

/* For the Macintosh environment when generating 68K applications */
#ifdef DB268K
   /* Before making any API calls for 68K environment, need to initialize the
      Library Manager */
   InitLibraryManager(0,kCurrentZone,kNormalMemory);
   atexit(CleanupLibraryManager);
#endif

  /* macro to initalize server, uid and pwd */
    INIT_UID_PWD;

    /* allocate an environment handle */
    rc = SQLAllocHandle(SQL_HANDLE_ENV, SQL_NULL_HANDLE, &henv);
    if (rc != SQL_SUCCESS) return ( terminate( henv, rc ));

    /* allocate a connect handle, and connect */
    rc = DBconnect( henv, &hdbc ) ;
    if ( rc != SQL_SUCCESS ) return( terminate( henv, rc ) ) ;

    rc = SQLAllocHandle( SQL_HANDLE_STMT, hdbc, &hstmt ) ;
    CHECK_HANDLE( SQL_HANDLE_DBC, hdbc, rc ) ;

/*--> */
    /* See what type of Asynchronous support is available,
     * and whether or not the CLI/ODBC configuration keyword ASYNCENABLE
     * is set on or off.
     */
    rc = SQLGetInfo( hdbc, /* Connection handle */
                     SQL_ASYNC_MODE, /* Query the support available */
                     &ubuffer, /* Store the result in this variable */
                     4, 
                     &outlen);
    CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;
	

    printf("SQL_ASYNC_MODE value from SQLGetInfo() is %s.\n\n",ASYNCMODE[ubuffer]);

    if (ubuffer == SQL_AM_NONE ) { /* Async not supported */
       printf("Asynchronous execution is not supported by this datasource\n");
       printf("or has been turned off by the CLI/ODBC configuration keyword\n");
       printf("ASYNCENABLE. The application will continue, ");
       printf("but SQLExecDirect()\nwill not be run asynchronously.\n\n");

       /* There is no need to set the SQLSetStmtAttr() option */
    } else {

       /* Set statement level asynchronous execution on */
       rc = SQLSetStmtAttr(
                hstmt,
                SQL_ATTR_ASYNC_ENABLE,
                (SQLPOINTER) SQL_ASYNC_ENABLE_ON,  
                0);
       CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;
    }


    /* The while loop is new for the asynchronous sample, the */
    /* SQLExecDirect() call remains the same. */ 
    while ((rc = SQLExecDirect(hstmt, sqlstmt, SQL_NTS) ) == SQL_STILL_EXECUTING) {
       printf("   ...SQLExecDirect() still executing asynchronously...\n");
       /* Other processing can be performed here, between each call
        * to see if SQLExecDirect() has finished running asynchronously.
        * This section will never run if CLI runs the function
        * synchronously.
        */
   }
	CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;

    rc = SQLBindCol(hstmt, 1, SQL_C_CHAR, (SQLPOINTER) deptname.s, 15,
                    &deptname.ind);
    CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;

    rc = SQLBindCol(hstmt, 2, SQL_C_CHAR, (SQLPOINTER) location.s, 15,
                    &location.ind);
    CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;

    printf("Departments in Eastern division:\n");
    printf("DEPTNAME       Location\n");
    printf("-------------- -------------\n");

    while ((rc = SQLFetch(hstmt)) == SQL_SUCCESS) {
        printf("%-14.14s %-14.14s \n", deptname.s, location.s);
    }
    if (rc != SQL_NO_DATA_FOUND)
        CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;

    /*  Commit the changes.  */
    rc = SQLEndTran( SQL_HANDLE_DBC, hdbc, SQL_COMMIT ) ;
    CHECK_HANDLE( SQL_HANDLE_DBC, hdbc, rc ) ;

    /*  Disconnect and free up CLI resources.  */

/*<-- */

    rc = SQLFreeHandle( SQL_HANDLE_STMT, hstmt ) ;
    CHECK_HANDLE( SQL_HANDLE_STMT, hstmt, rc ) ;

    printf( "\n>Disconnecting .....\n" ) ;
    rc = SQLDisconnect( hdbc ) ;
    CHECK_HANDLE( SQL_HANDLE_DBC, hdbc, rc ) ;

    rc = SQLFreeHandle( SQL_HANDLE_DBC, hdbc ) ;
    CHECK_HANDLE( SQL_HANDLE_DBC, hdbc, rc ) ;

    rc = SQLFreeHandle( SQL_HANDLE_ENV,  henv ) ;
    if ( rc != SQL_SUCCESS ) return( terminate( henv, rc ) ) ;

    return( SQL_SUCCESS ) ;


}                               /* end main */