home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 8 Other / 08-Other.zip / rsql.zip / RSQL.C < prev    next >
C/C++ Source or Header  |  1994-01-13  |  56KB  |  1,373 lines

  1. static unsigned char sqla_program_id[40] = 
  2. {111,65,65,66,65,69,67,67,78,70,85,32,32,32,32,32,82,83,81,76,
  3. 32,32,32,32,75,65,99,81,79,78,66,75,48,32,32,32,32,32,32,32};
  4.  
  5.  
  6. /* Operating System Control Parameters */
  7. #ifndef SQL_API_RC
  8. #define SQL_STRUCTURE struct
  9. #define SQL_API_RC int
  10. #define SQL_POINTER
  11. #ifdef  SQL16TO32
  12. #define SQL_API_FN far pascal _loadds
  13. #else
  14. #define SQL_API_FN _System
  15. #endif
  16. #endif
  17.  
  18. struct sqlca;
  19. struct sqlda;
  20. SQL_API_RC SQL_API_FN  sqlaaloc(unsigned short,
  21.                                 unsigned short,
  22.                                 unsigned short,
  23.                                 void *);
  24. SQL_API_RC SQL_API_FN  sqlacall(unsigned short,
  25.                                 unsigned short,
  26.                                 unsigned short,
  27.                                 unsigned short,
  28.                                 void *);
  29. SQL_API_RC SQL_API_FN  sqladloc(unsigned short,
  30.                                 void *);
  31. SQL_API_RC SQL_API_FN  sqlasets(unsigned short,
  32.                                 void *,
  33.                                 void *);
  34. SQL_API_RC SQL_API_FN  sqlasetv(unsigned short,
  35.                                 unsigned short,
  36.                                 unsigned short,
  37.                                 unsigned short,
  38.                                 void *,
  39.                                 void *,
  40.                                 void *);
  41. SQL_API_RC SQL_API_FN  sqlastop(void *);
  42. SQL_API_RC SQL_API_FN  sqlastrt(void *,
  43.                                 void *,
  44.                                 struct sqlca *);
  45. SQL_API_RC SQL_API_FN  sqlausda(unsigned short,
  46.                                 struct sqlda *,
  47.                                 void *);
  48. SQL_API_RC SQL_API_FN  sqlestrd_api(unsigned char *,
  49.                                     unsigned char *,
  50.                                     unsigned char,
  51.                                     struct sqlca *);
  52. SQL_API_RC SQL_API_FN  sqlestpd_api(struct sqlca *);
  53. #line 1 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  54. /*****************************************************************************/
  55. /*  PROGRAM NAME:  RSQL.SQC          -- Run SQL Program                      */
  56. /*                                                                           */
  57. /*  DESCRIPTION:  This program allows a user to run a batch file consisting  */
  58. /*    of SQL and Database Administrator commands against an OS/2 database.   */
  59. /*    The script is submitted to RSQL in a command file and the results      */
  60. /*    appear in a response file.  RSQL runs as an OS/2 task and does not     */
  61. /*    require the services of Query Manager.                                 */
  62. /*                                                                           */
  63. /*  PROGRAM INVOCATION:                                                      */
  64. /*                                                                           */
  65. /*    rsql cmd_file resp_file                                                */
  66. /*                                                                           */
  67. /*         cmd_file  = run file that contains the user script                */
  68. /*         resp_file = response file that contains the output                */
  69. /*                                                                           */
  70. /*****************************************************************************/
  71. #include <process.h>                        /* For exit()                    */
  72. #include <stdio.h>                          /* for printf() and NULL         */
  73. #include <stdlib.h>                         /* for printf()                  */
  74. #include <string.h>                         /* for printf()                  */
  75. #include <sys\types.h>                      /* for _ftime()                  */
  76. #include <sys\timeb.h>                      /* for _ftime()                  */
  77. #include <io.h>                             /* for file I/O                  */
  78. #include <conio.h>                          /* for getch and kbhit           */
  79. #include <fcntl.h>                          /* for file I/O                  */
  80.  
  81. #define INCL_DOSMEMMGR
  82. #define INCL_DOSPROCESS
  83. #include <os2.h>
  84.  
  85. #include <sqlca.h>                          /* for sqlca                     */
  86. #include <sql.h>                            /* for error msg retrieval       */
  87. #include <sqlcodes.h>                       /* for SQL return code constants */
  88. #include <sqlenv.h>                         /* for environment functions     */
  89. #include <sqlutil.h>                        /* for utility functions         */
  90. #include <upm.h>                            /* for logon/logoff functions    */
  91. struct sqlca sqlca;                         /* for DB mgr return codes       */
  92.  
  93. #include "rsql.h"
  94. #pragma stack16(8192)
  95.  
  96. /*___________________________________________________________________________*/
  97. /* Main function                                                             */
  98. /*___________________________________________________________________________*/
  99. int main(int argc, char **argv)
  100. {
  101.    SHORT cmd_type;
  102.    SHORT ch;
  103.  
  104.    initialize_rsql();
  105.    check_args_and_prepare_files(argc, argv);
  106.  
  107.    /*_____________________________________________*/
  108.    /* Process commands one at a time              */
  109.    /*_____________________________________________*/
  110.    while (!feof(cmd_stream))
  111.     /*_____________________________________________*/
  112.     /* get next command                            */
  113.     /*_____________________________________________*/
  114.     {
  115.      cmd_type = get_command(parm_buf);
  116.      /*_____________________________________________*/
  117.      /* Initialize timer                            */
  118.      /*_____________________________________________*/
  119.      reset_timer();
  120.      start_timer();
  121.      /*_____________________________________________*/
  122.      /* Execute the command                         */
  123.      /*_____________________________________________*/
  124.      switch (cmd_type) {
  125.                        /*_____________________________________________*/
  126.                        /* Dynamic SQL commands                        */
  127.                        /*_____________________________________________*/
  128.      case CMD_SQL_IMMEDIATE         : rcd = sql_immediate(parm_buf);     break;
  129.      case CMD_SQL_SELECT            : rcd = sql_select(parm_buf);        break;
  130.                        /*_____________________________________________*/
  131.                        /* Execute an OS/2 program                     */
  132.                        /*_____________________________________________*/
  133.      case CMD_DOS                   : rcd = dos_exec(parm_buf);          break;
  134.                        /*_____________________________________________*/
  135.                        /* Database Administration commands            */
  136.                        /*_____________________________________________*/
  137.      case CMD_DBA                   : rcd = dba_exec(parm_buf);          break;
  138.                        /*_____________________________________________*/
  139.                        /* RSQL execution controls                     */
  140.                        /*_____________________________________________*/
  141.      case CMD_DBA_CONTINUE_ON_ERROR : rcd = RECORD_NOTHING;
  142.                                       continue_on_error = TRUE;          break;
  143.      case CMD_DBA_STOP_ON_ERROR     : rcd = RECORD_NOTHING;
  144.                                       continue_on_error = FALSE;         break;
  145.      case CMD_DBA_PAUSE             : rcd = RECORD_NOTHING;
  146.                                       printf("\nPausing! Press any key "
  147.                                              "to continue...");
  148.                                       while (!kbhit());
  149.                                       ch = getch();
  150.                                       break;
  151.      case CMD_SYNTAX_ERROR          : rcd = RECORD_ERR_MSG;              break;
  152.      case CMD_NO_CMD                : rcd = RECORD_NOTHING;              break;
  153.      default: break;
  154.      } /* endswitch */
  155.      /*_____________________________________________*/
  156.      /* Stop the timer, record the results,         */
  157.      /* terminate command processing if error       */
  158.      /*_____________________________________________*/
  159.      stop_timer();
  160.      if (record_command_results(rcd) == TERMINATE)
  161.         break;
  162.  
  163.    } /* endwhile */
  164.  
  165.    terminate_program();
  166.  
  167. }  /* end main */
  168.  
  169.  
  170. /*___________________________________________________________________________*/
  171. /* Perform required program initialization                                   */
  172. /*___________________________________________________________________________*/
  173. VOID initialize_rsql(VOID)
  174. {
  175.      /*_____________________________________________*/
  176.      /* Allocate an SQLDA                           */
  177.      /*_____________________________________________*/
  178.      sqlda = (struct sqlda *)malloc(SQLDASIZE(255));
  179.  
  180.      /*_____________________________________________*/
  181.      /* Enable the exit list procedure              */
  182.      /*_____________________________________________*/
  183.      DosExitList(1,                       /* 1 = Add to exit list */
  184.                 (PFNEXITLIST) exit_proc);  /* pointer to procedure */
  185.  
  186. } /* end initialize_rsql */
  187.  
  188.  
  189. /*___________________________________________________________________________*/
  190. /* Check for the right number of program arguments and open files            */
  191. /*___________________________________________________________________________*/
  192. VOID check_args_and_prepare_files(USHORT argc, PCHAR argv[])
  193. {
  194.      /*_____________________________________________*/
  195.      /* Are the required parameters there?          */
  196.      /*_____________________________________________*/
  197.      if (argc < 3) {
  198.         fprintf(stderr,"\nCalling syntax is: rsql run_file resp_file");
  199.         exit(1);
  200.      } /* endif */
  201.      /*_____________________________________________*/
  202.      /* Open the RUN and RESPONSE files             */
  203.      /*_____________________________________________*/
  204.      if (NULL == (cmd_stream = fopen(argv[1], "r"))) {
  205.         printf("\nError opening the RUN file : %s", argv[1]);
  206.         exit(1);
  207.      } /* endif */
  208.      if (NULL == (out_stream = fopen(argv[2], "w"))) {
  209.         printf("\nError opening the RESPONSE file : %s", argv[2]);
  210.         exit(1);
  211.      } /* endif */
  212.  
  213. } /* end check_args_and_prepare_file */
  214.  
  215.  
  216.  
  217. /*___________________________________________________________________________*/
  218. /* Cleanup and terminate the program                                         */
  219. /*___________________________________________________________________________*/
  220. VOID terminate_program(VOID)
  221. {
  222.    free(sqlda);
  223.    fclose(cmd_stream);
  224.    fclose(out_stream);
  225. } /* end terminate_program */
  226.  
  227.  
  228.  
  229. /*___________________________________________________________________________*/
  230. /* This procedure displays how the program terminated and performs cleanup   */
  231. /* if abnormal termination.                                                  */
  232. /*___________________________________________________________________________*/
  233. VOID exit_proc(ULONG term_code)
  234. {
  235.    /*_____________________________________________*/
  236.    /* Determine termination cause                 */
  237.    /*_____________________________________________*/
  238.    switch (term_code) {
  239.    case  0:
  240.       printf("\n**program terminated normally**\n");
  241.       break;
  242.    case  1:
  243.       printf("\n**program terminated by hard error**\n");
  244.       break;
  245.    case  2:
  246.       fclose(cmd_stream);
  247.       fclose(out_stream);
  248.       printf("\n**program terminated by a trap**\n");
  249.       break;
  250.    case  3:
  251.       fclose(cmd_stream);
  252.       fclose(out_stream);
  253.       printf("\n**program terminated by a DOSKillProcess**\n");
  254.       break;
  255.    default:
  256.       printf("\n**unknown program termination**\n");
  257.    } /* endswitch */
  258.    /*_____________________________________________*/
  259.    /* Allow next exit list                        */
  260.    /*_____________________________________________*/
  261.    DosExitList(3,                                  /* 3 allows next exit to run */
  262.                (void far *) 0);                    /* null pointer              */
  263. } /* end exit_proc */
  264.  
  265.  
  266.  
  267. /*___________________________________________________________________________*/
  268. /* This procedure determines the command type                                */
  269. /*___________________________________________________________________________*/
  270. SHORT get_command(PCHAR parm_str)
  271. {
  272.   char cmd[MAX_CMD_SIZE];          /* temp buffer for cmd processing */
  273.   char token1[5];                  /* token to receive EXEC          */
  274.   char token2[5];                  /* token to receive DBA: or SQL:  */
  275.   char token3[25];                 /* token to receive cmd name      */
  276.   char token4[MAX_CMD_SIZE];       /* token to receive parms         */
  277.   char comment_line[MAX_CMD_SIZE]; /* comment line temp variable     */
  278.   char delim1,delim2;              /* variables for sscanf           */
  279.  
  280.   /*_____________________________________________*/
  281.   /* Initialize cmds table                       */
  282.   /*_____________________________________________*/
  283.   typedef struct
  284.   {
  285.     CHAR    cmd_name[40];            /*  cmd name                   */
  286.     CHAR    cmd_num;                 /* numerical representation    */
  287.     USHORT  num_parms;               /* no. of parms for this cmd   */
  288.   }   CMD_TYPE;
  289.  
  290.   static CMD_TYPE cmds[] =
  291.   {/*<=== cmd_name ---><-- cmd_num -----------------><-- num_parms -->*/
  292.    {"BACKUP",           CMD_DBA_BACKUP             ,  3               },
  293.    {"BIND",             CMD_DBA_BIND               ,  6               },
  294.    {"CATALOG_DB",       CMD_DBA_CATALOG_DB         ,  6               },
  295.    {"CATALOG_NODE",     CMD_DBA_CATALOG_NODE       ,  4               },
  296.    {"COLLECT_STATUS",   CMD_DBA_COLLECT_STATUS     ,  1               },
  297.    {"CONTINUE_ON_ERROR",CMD_DBA_CONTINUE_ON_ERROR  ,  0               },
  298.    {"CREATE_DB",        CMD_DBA_CREATE_DB          ,  3               },
  299.    {"DROP_DB",          CMD_DBA_DROP_DB            ,  1               },
  300.    {"EXPORT",           CMD_DBA_EXPORT             ,  4               },
  301.    {"GET_ADMIN",        CMD_DBA_GET_ADMIN          ,  0               },
  302.    {"IMPORT",           CMD_DBA_IMPORT             ,  5               },
  303.    {"LOGOFF",           CMD_DBA_LOGOFF             ,  3               },
  304.    {"LOGON",            CMD_DBA_LOGON              ,  5               },
  305.    {"PAUSE",            CMD_DBA_PAUSE              ,  0               },
  306.    {"REORG",            CMD_DBA_REORG              ,  3               },
  307.    {"RESET_DM_CFG",     CMD_DBA_RESET_DM_CFG       ,  0               },
  308.    {"RESET_DB_CFG",     CMD_DBA_RESET_DB_CFG       ,  1               },
  309.    {"RESTORE",          CMD_DBA_RESTORE            ,  3               },
  310.    {"ROLL_FORWARD",     CMD_DBA_ROLL_FORWARD       ,  3               },
  311.    {"RUNSTATS",         CMD_DBA_RUNSTATS           ,  1               },
  312.    {"SHOW_DB_CFG",      CMD_DBA_SHOW_DB_CFG        ,  1               },
  313.    {"SHOW_DB_DIR",      CMD_DBA_SHOW_DB_DIR        ,  1               },
  314.    {"SHOW_DM_CFG",      CMD_DBA_SHOW_DM_CFG        ,  0               },
  315.    {"SHOW_NODE_DIR",    CMD_DBA_SHOW_NODE_DIR      ,  0               },
  316.    {"STARTDM",          CMD_DBA_STARTDM            ,  0               },
  317.    {"STARTUSE",         CMD_DBA_STARTUSE           ,  2               },
  318.    {"STOPDM",           CMD_DBA_STOPDM             ,  0               },
  319.    {"STOP_ON_ERROR",    CMD_DBA_STOP_ON_ERROR      ,  0               },
  320.    {"STOPUSE",          CMD_DBA_STOPUSE            ,  0               },
  321.    {"UNCATALOG_DB",     CMD_DBA_UNCATALOG_DB       ,  1               },
  322.    {"UNCATALOG_NODE",   CMD_DBA_UNCATALOG_NODE     ,  1               },
  323.    {"UPDATE_DB_CFG",    CMD_DBA_UPDATE_DB_CFG      ,  2               },
  324.    {"UPDATE_DM_CFG",    CMD_DBA_UPDATE_DM_CFG      ,  0               },
  325.   };
  326.   USHORT      cmd_not_found;     /* True if a match is found          */
  327.   USHORT      i;                 /* Loop index variable               */
  328.   PCHAR       char_ptr;          /* used to remove CRLF from SQL stmts*/
  329.   /*_____________________________________________*/
  330.   /* Read a command from the RUN file            */
  331.   /*_____________________________________________*/
  332.    num_parms = fscanf(cmd_stream," %[^;]%*c ", cmd);
  333.    if (num_parms == EOF) {
  334.       return(CMD_NO_CMD);                       /* empty file          */
  335.    strcat(cmd,";");                             /* maintain cmd delim. */
  336.    } /* endif */
  337.    /*_____________________________________________*/
  338.    /* Echo command to the response file           */
  339.    /*_____________________________________________*/
  340.    fprintf(out_stream, "%s\n", cmd);
  341.  
  342.    /*_____________________________________________*/
  343.    /* Remove any comment lines                    */
  344.    /*_____________________________________________*/
  345.    while ((cmd[0] == '-') && (cmd[1] == '-')) {
  346.       num_parms = sscanf(cmd,"%[^\n;]%c %[^;]%c ",
  347.                   comment_line, &delim1, cmd, &delim2);  /* remove comment line */
  348.       if (delim1 == ';') {
  349.          return (CMD_NO_CMD);                            /* maintain cmd delim */
  350.       } /* endif */
  351.    } /* endwhile */
  352.  
  353.    /*_____________________________________________*/
  354.    /* Parse the command and make some validity    */
  355.    /* checks                                      */
  356.    /*_____________________________________________*/
  357.    num_parms = sscanf(cmd, " %4s %4s %24s %[^;]",
  358.                          token1, token2, token3, token4);
  359.  
  360.    if (num_parms == 3) {                                 /* no parms, parse accordingly */
  361.       num_parms = sscanf(cmd, " %4s %4s %24[^;]",
  362.                          token1, token2, token3);
  363.       strcpy(token4,"");
  364.    } /* endif */
  365.  
  366.    if ((num_parms <3)                      ||
  367.        (strcmp(token1,"EXEC") != 0)        ||
  368.        ((strcmp(token2,"DBA:") != 0)       &&
  369.         (strcmp(token2,"DOS:") != 0)       &&
  370.         (strcmp(token2,"SQL:") != 0)))     {
  371.       sprintf(err_msg,
  372.       "\nSYNTAX ERROR: Expected EXEC (SQL or DBA etc...) to begin a command.");
  373.       return(CMD_SYNTAX_ERROR);
  374.    } /* endif */
  375.  
  376.    /*_____________________________________________*/
  377.    /* SQL CMD, return command type,               */
  378.    /* remove EXEC SQL                             */
  379.    /*_____________________________________________*/
  380.      if (strcmp(token2,"SQL:") == 0) {
  381.         char_ptr = strpbrk(token4,"\n\r");              /* remove CRLF chars */
  382.         while (char_ptr != NULL) {
  383.            char_ptr[0] = ' ';
  384.            char_ptr = strpbrk(char_ptr,"\n\r");
  385.         } /* endwhile */
  386.         sprintf(parm_str, "%s %s", token3, token4);     /* return the cmd for */
  387.         if (strcmp(strupr(token3),"SELECT") == 0) {     /* for processing     */
  388.            return(CMD_SQL_SELECT);
  389.         } else {
  390.            return(CMD_SQL_IMMEDIATE);
  391.         } /* endif */
  392.      } /* endif */
  393.  
  394.    /*_____________________________________________*/
  395.    /* DOS CMD, return command type,               */
  396.    /* remove EXEC DOS                             */
  397.    /*_____________________________________________*/
  398.    if (strcmp(token2,"DOS:") == 0) {
  399.       sprintf(parm_str, "%s%c%s", token3, 0, token4);   /* return the cmd     */
  400.                                                         /* in the form for    */
  401.                                                         /* DOSExecPgm         */
  402.       return(CMD_DOS);
  403.    } /* endif */
  404.  
  405.    /*_____________________________________________*/
  406.    /* DBA CMD, return command type,               */
  407.    /* remove EXEC DBA: cmd_name"                  */
  408.    /*_____________________________________________*/
  409.    i=0;
  410.    cmd_not_found = TRUE;
  411.  
  412.    while (cmd_not_found && (i < CMD_LAST_CMD)) {
  413.       cmd_not_found = strcmp(cmds[i].cmd_name,token3);
  414.       if (!cmd_not_found) {
  415.          break;
  416.       } else {
  417.          i++;
  418.       } /* endif */
  419.    } /* endwhile */
  420.  
  421.    if (cmd_not_found) {
  422.       sprintf(err_msg,
  423.       "\nSYNTAX ERROR: Unknown Command. ");
  424.       return(CMD_SYNTAX_ERROR);
  425.    } /* endif */
  426.  
  427.    if ((cmds[i].cmd_num == CMD_DBA_CONTINUE_ON_ERROR) ||
  428.        (cmds[i].cmd_num == CMD_DBA_STOP_ON_ERROR) ||
  429.        (cmds[i].cmd_num == CMD_DBA_PAUSE))  {
  430.       return(cmds[i].cmd_num);
  431.    } /* endif */
  432.  
  433.    sprintf(parm_str, "%s", token4);
  434.    strcpy(parms.cmd_name,cmds[i].cmd_name);
  435.    parms.cmd_num = cmds[i].cmd_num;
  436.    parms.num_parms = cmds[i].num_parms;
  437.    return(CMD_DBA);
  438.  
  439. } /* end get_command */
  440.  
  441.  
  442.  
  443. /*___________________________________________________________________________*/
  444. /* This procedure initializes the time variable                              */
  445. /*___________________________________________________________________________*/
  446. VOID  reset_timer(VOID)
  447. {
  448.    event_time = 0.0;
  449.    start_time = 0.0;
  450.    end_time   = 0.0;
  451. } /* end reset_timer */
  452.  
  453.  
  454.  
  455. /*___________________________________________________________________________*/
  456. /* This procedure records the time at the start of an interval               */
  457. /*___________________________________________________________________________*/
  458. VOID  start_timer(VOID)
  459. {
  460.    _ftime(&timebuff);
  461.    start_time=(double)timebuff.time+((double)timebuff.millitm)/(double)1000;
  462. } /* end start_timer */
  463.  
  464.  
  465.  
  466. /*___________________________________________________________________________*/
  467. /* This procedure records the time at the end of an interval                 */
  468. /* and calculates the elapsed time for an event.                             */
  469. /*___________________________________________________________________________*/
  470. VOID  stop_timer(VOID)
  471. {
  472.    _ftime(&timebuff);
  473.    end_time=(double)timebuff.time+((double)timebuff.millitm)/(double)1000;
  474.    event_time = event_time + (end_time - start_time);
  475.  
  476. } /* end stop_timer */
  477.  
  478.  
  479.  
  480.  
  481. /*___________________________________________________________________________*/
  482. /* This procedure executes an SQL command dynamically (non SELECT)           */
  483. /*___________________________________________________________________________*/
  484. SHORT sql_immediate(PCHAR cmd_sql)
  485. {
  486.    /*_____________________________________________*/
  487.    /* Declare cmd to DB2/2                        */
  488.    /*_____________________________________________*/
  489.    
  490. /*
  491. EXEC SQL BEGIN DECLARE SECTION;
  492. */
  493. #line 436 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  494.  
  495.       char     *  cmd;
  496.    
  497. /*
  498. EXEC SQL END DECLARE SECTION;
  499. */
  500. #line 438 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  501.  
  502.    cmd = cmd_sql;
  503.    /*_____________________________________________*/
  504.    /* Execute cmd                                 */
  505.    /*_____________________________________________*/
  506.    
  507. /*
  508. EXEC SQL EXECUTE IMMEDIATE :cmd;
  509. */
  510.  
  511. {
  512.   sqlastrt(sqla_program_id,0L,&sqlca);
  513.   sqlasets(strlen(cmd),cmd,0L);
  514.   sqlacall((unsigned short)23,1,0,0,0L);
  515.   sqlastop(0L);
  516. }
  517. #line 443 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  518.  
  519.  
  520.    return (RECORD_SQLCA);
  521. } /* end sql_immediate */
  522.  
  523.  
  524.  
  525.  
  526. /*___________________________________________________________________________*/
  527. /* This procedure executes an SQL command dynamically (SELECT)               */
  528. /*___________________________________________________________________________*/
  529. SHORT sql_select(PCHAR cmd)
  530. {
  531.    SHORT    index, i;                           /* for counting                  */
  532.    SHORT    num_of_rows;                        /* number of rows selected       */
  533.    SHORT    num_brk;                            /* number of rows since break    */
  534.    SHORT    byte_count;                         /* number of bytes to allocate   */
  535.    /*_____________________________________________*/
  536.    /* Declare cmd to DB2/2                        */
  537.    /*_____________________________________________*/
  538.    
  539. /*
  540. EXEC SQL BEGIN DECLARE SECTION;
  541. */
  542. #line 463 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  543.  
  544.       char     *  cmd_sql;                      /* command buffer                */
  545.    
  546. /*
  547. EXEC SQL END DECLARE SECTION;
  548. */
  549. #line 465 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  550.  
  551.  
  552.    cmd_sql     = cmd;
  553.    num_of_rows = 0;
  554.    num_brk     = 0;
  555.  
  556.    /*_____________________________________________*/
  557.    /* Initialize the SQLDA                        */
  558.    /*_____________________________________________*/
  559.    strncpy(sqlda->sqldaid,"SQLDA   ",8);
  560.    sqlda->sqldabc = (long) SQLDASIZE(255);
  561.    sqlda->sqln = SQLVAR_NUM;
  562.    sqlda->sqld = 0;
  563.  
  564.    /*_____________________________________________*/
  565.    /* Prepare cmd                                 */
  566.    /*_____________________________________________*/
  567.    
  568. /*
  569. EXEC SQL PREPARE st into :*sqlda FROM :cmd_sql;
  570. */
  571.  
  572. {
  573.   sqlastrt(sqla_program_id,0L,&sqlca);
  574.   sqlausda(3,&*sqlda,0L);
  575.   sqlasets(strlen(cmd_sql),cmd_sql,0L);
  576.   sqlacall((unsigned short)27,2,0,3,0L);
  577.   sqlastop(0L);
  578. }
  579. #line 482 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  580.  
  581.    if (SQLCODE != 0) {
  582.       return(RECORD_SQLCA);
  583.    } /* endif */
  584.  
  585.    /*_____________________________________________*/
  586.    /* Stop timer                                  */
  587.    /*_____________________________________________*/
  588.    stop_timer();
  589.  
  590.    /*_____________________________________________*/
  591.    /* Allocate space for select variables         */
  592.    /*_____________________________________________*/
  593.    for (index=0;index<sqlda->sqld ;index++ ) {
  594.       if ((sqlda->sqlvar[index].sqltype == SQL_TYP_DECIMAL) ||
  595.           (sqlda->sqlvar[index].sqltype == SQL_TYP_NDECIMAL))  {
  596.          byte_count = (LOBYTE(sqlda->sqlvar[index].sqllen) + 2)/2;
  597.       } else {
  598.          byte_count = sqlda->sqlvar[index].sqllen;
  599.       } /* endif */
  600.  
  601.       sqlda->sqlvar[index].sqldata = (unsigned char *)malloc(byte_count);
  602.       if (sqlda->sqlvar[index].sqldata == NULL) {
  603.          fprintf(out_stream,
  604.          "\nOut of dynamic memory while space for select column %d",index+1);
  605.          return(RECORD_ERR_MSG);
  606.       } /* endif */
  607.  
  608.       /*_____________________________________________*/
  609.       /* Allocate space for null indicators          */
  610.       /*_____________________________________________*/
  611.       if (sqlda->sqlvar[index].sqltype & 1) {         /* odd   */
  612.          sqlda->sqlvar[index].sqlind = (short *)malloc(2);
  613.          if (sqlda->sqlvar[index].sqldata == NULL) {
  614.             fprintf(out_stream,
  615.             "\nOut of dynamic memory while space for NULL column %d", index+1);
  616.             return(RECORD_ERR_MSG);
  617.          } /* endif */
  618.       } /* endif */
  619.    } /* endfor */
  620.  
  621.    rcd = print_format_row(SET_TABS_WIDTH);
  622.    if (rcd != 0) {
  623.       return(RECORD_ERR_MSG);
  624.    } /* endif */
  625.  
  626.    rcd = print_format_row(PRINT_COLUMNS);
  627.    if (rcd != 0) {
  628.       return(RECORD_ERR_MSG);
  629.    } /* endif */
  630.  
  631.    /*_____________________________________________*/
  632.    /* Start timer                                 */
  633.    /*_____________________________________________*/
  634.  
  635.    start_timer();
  636.  
  637.    
  638. /*
  639. EXEC SQL DECLARE cur CURSOR for st;
  640. */
  641. #line 539 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  642.  
  643.    if (SQLCODE != 0) {
  644.       return(RECORD_SQLCA);
  645.    } /* endif */
  646.  
  647.    
  648. /*
  649. EXEC SQL OPEN cur;
  650. */
  651.  
  652. {
  653.   sqlastrt(sqla_program_id,0L,&sqlca);
  654.   sqlacall((unsigned short)26,2,0,0,0L);
  655.   sqlastop(0L);
  656. }
  657. #line 544 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  658.  
  659.    if (SQLCODE != 0) {
  660.       return(RECORD_SQLCA);
  661.    } /* endif */
  662.  
  663.    /*_____________________________________________*/
  664.    /* Handle data one row at a time               */
  665.    /*_____________________________________________*/
  666.    
  667. /*
  668. EXEC SQL FETCH cur USING DESCRIPTOR :*sqlda;
  669. */
  670.  
  671. {
  672.   sqlastrt(sqla_program_id,0L,&sqlca);
  673.   sqlausda(3,&*sqlda,0L);
  674.   sqlacall((unsigned short)25,2,0,3,0L);
  675.   sqlastop(0L);
  676. }
  677. #line 552 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  678.  
  679.    if ((SQLCODE !=0) && (SQLCODE != SQL_RC_W100)) {
  680.       return(RECORD_SQLCA);
  681.    } /* endif */
  682.  
  683.    while (SQLCODE == 0l) {
  684.       stop_timer();
  685.       num_of_rows++;
  686.       if (num_brk++ > BREAK_SEP) {
  687.          for (i=0;i<BREAK_ROWS ;i++ ) {
  688.             fputs("\n",out_stream);
  689.          } /* endfor */
  690.          print_format_row(PRINT_COLUMNS);
  691.          num_brk = 0;
  692.       } /* endif */
  693.       rcd=print_format_row(PRINT_SELECTED_ROW);
  694.       if (rcd != 0) {
  695.          return(RECORD_ERR_MSG);
  696.       } else {
  697.          start_timer();
  698.          
  699. /*
  700. EXEC SQL FETCH cur USING DESCRIPTOR :*sqlda;
  701. */
  702.  
  703. {
  704.   sqlastrt(sqla_program_id,0L,&sqlca);
  705.   sqlausda(3,&*sqlda,0L);
  706.   sqlacall((unsigned short)25,2,0,3,0L);
  707.   sqlastop(0L);
  708. }
  709. #line 572 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  710.  
  711.          if ((SQLCODE !=0) && (SQLCODE != SQL_RC_W100)) {
  712.             return(RECORD_SQLCA);
  713.          } /* endif */
  714.       } /* endif */
  715.    } /* endwhile */
  716.  
  717.    
  718. /*
  719. EXEC SQL CLOSE cur;
  720. */
  721.  
  722. {
  723.   sqlastrt(sqla_program_id,0L,&sqlca);
  724.   sqlacall((unsigned short)20,2,0,0,0L);
  725.   sqlastop(0L);
  726. }
  727. #line 579 "H:\\IBMWF\\PRJ\\RSQL\\.\\RSQL.SQC"
  728.  
  729.    if (SQLCODE != 0) {
  730.       return(RECORD_SQLCA);
  731.    } /* endif */
  732.  
  733.    /*_____________________________________________*/
  734.    /* Stop timer                                  */
  735.    /*_____________________________________________*/
  736.  
  737.    stop_timer();
  738.    fprintf(out_stream,"\n\n Total Number of Rows SELECTED = %d\n",num_of_rows);
  739.  
  740.    /*_____________________________________________*/
  741.    /* Free space for select variables             */
  742.    /*_____________________________________________*/
  743.    for (index=0;index < sqlda->sqld ;index++ ) {
  744.       free(sqlda->sqlvar[index].sqldata);
  745.  
  746.    /*_____________________________________________*/
  747.    /* Free space for null indicators              */
  748.    /*_____________________________________________*/
  749.       if (sqlda->sqlvar[index].sqltype & 1) {                  /*   odd    */
  750.          free(sqlda->sqlvar[index].sqlind);
  751.       } /* endif */
  752.    } /* endfor */
  753.  
  754.    return(RECORD_SQLCA);
  755.  
  756. } /* end sql_select */
  757.  
  758.  
  759.  
  760.  
  761. /*___________________________________________________________________________*/
  762. /*  This procedure performs the requested format actions:                    */
  763. /*                                                                           */
  764. /*  SET_TABS_WIDTH calculates the tab position for each field in a query     */
  765. /*  PRINT_COLUMNS  formats one row of columns using the tabs and sqlda       */
  766. /*  PRINT_SELECTED_ROW                                                       */
  767. /*                 formats one SELECT row using the tabs and sqlda           */
  768. /*___________________________________________________________________________*/
  769. SHORT print_format_row(USHORT action)
  770. {
  771.    #define      MAX_FLDS     50              /* for this exercise             */
  772.    SHORT        index, i, y;                 /*  for counting                 */
  773.    CHAR         row[MAX_LINE_SIZE+1];        /* row to be printed             */
  774.    CHAR         temp[MAX_LINE_SIZE+10];      /* temp buffer                   */
  775.    CHAR         temp1[100];                  /* 2nd temp buffer               */
  776.    typedef struct
  777.    {
  778.       SHORT    tab_pos;                      /* column position               */
  779.       SHORT    max_width;                    /* max_width str width of type   */
  780.    }  FLD_TYPE;
  781.    static FLD_TYPE   field[MAX_FLDS];        /* contains field descriptors    */
  782.    SHORT          col_name_width;            /* width of col name             */
  783.    SHORT          col_fld_width;             /* width of col fld              */
  784.    static SHORT   max_num_flds;              /* number of printable columns   */
  785.    SHORT          null_not_found;            /* a flag                        */
  786.    USHORT         top, precision, scale;     /* for decimal fields            */
  787.    SHORT          bottom, point;             /* for decimal fields            */
  788.    SHORT          len;                       /* for decimal fields            */
  789.    UCHAR          *ptr;                      /* for decimal fields            */
  790.    BOOL           output_blank;              /* for decimal fields            */
  791.  
  792.    /*_____________________________________________*/
  793.    /* Initialize                                  */
  794.    /*_____________________________________________*/
  795.    memset(row,' ',sizeof(row));
  796.    row[sizeof(row) - 1] = '\0';
  797.    i = 0;
  798.    rcd = GOOD;
  799.  
  800.    /*_____________________________________________*/
  801.    /* Do action                                   */
  802.    /*_____________________________________________*/
  803.    switch (action) {
  804.    case  SET_TABS_WIDTH:
  805.       field[0].tab_pos = 1;                  /* Start with column 1           */
  806.       for (index=0;index < sqlda->sqld ;index++ ) {
  807.          col_name_width = sqlda->sqlvar[index].sqlname.length;
  808.          col_fld_width  = sqlda->sqlvar[index].sqllen;
  809.  
  810.          switch (sqlda->sqlvar[index].sqltype) {
  811.          case SQL_TYP_INTEGER:
  812.          case SQL_TYP_NINTEGER:
  813.          case SQL_TYP_FLOAT:
  814.          case SQL_TYP_NFLOAT:
  815.             col_fld_width = 11;
  816.             break;
  817.          case SQL_TYP_SMALL:
  818.          case SQL_TYP_NSMALL:
  819.             col_fld_width = 6;
  820.             break;
  821.          case SQL_TYP_DECIMAL:
  822.          case SQL_TYP_NDECIMAL:
  823.             col_fld_width = LOBYTE(sqlda->sqlvar[index].sqllen) + 1;
  824.                                              /* precision + decimal point     */
  825.             break;
  826.          case SQL_TYP_DATE:
  827.          case SQL_TYP_NDATE:
  828.             col_fld_width=10;
  829.             break;
  830.          case SQL_TYP_TIME:
  831.          case SQL_TYP_NTIME:
  832.             col_fld_width=8;
  833.             break;
  834.          case SQL_TYP_STAMP:
  835.          case SQL_TYP_NSTAMP:
  836.             col_fld_width=26;
  837.             break;
  838.          default:
  839.             break;
  840.          } /* endswitch */
  841.          /*_____________________________________________*/
  842.          /* Use the larger of col_name or col_fld       */
  843.          /*_____________________________________________*/
  844.          if (col_name_width > col_fld_width) {
  845.             field[index].max_width = col_name_width;
  846.          } else {
  847.             field[index].max_width = col_fld_width;
  848.          } /* endif */
  849.          /*_____________________________________________*/
  850.          /* Update tab field 1 space between columns    */
  851.          /*_____________________________________________*/
  852.          field[index+1].tab_pos = field[index].tab_pos +
  853.                                     field[index].max_width +
  854.                                     COL_SEP;
  855.          /*_____________________________________________*/
  856.          /* Check Limits                                */
  857.          /*_____________________________________________*/
  858.          if (field[index+1].tab_pos > MAX_LINE_SIZE) {
  859.             max_num_flds = index;
  860.             break;                           /*  out of for loop              */
  861.          } else {
  862.             max_num_flds = index + 1;
  863.          } /* endif */
  864.  
  865.          if (max_num_flds > MAX_FLDS) {
  866.             break;                           /*  out of for loop              */
  867.          } /* endif */
  868.  
  869.       } /* endfor */
  870.  
  871.       break;                                 /* end of action SET_TABS_WIDTH  */
  872.  
  873.    case PRINT_COLUMNS:
  874.       /*_____________________________________________*/
  875.       /* Print column names                          */
  876.       /*_____________________________________________*/
  877.       for (index=0;index < max_num_flds ;index++ ) {
  878.          memcpy(&row[field[index].tab_pos],
  879.                 sqlda->sqlvar[index].sqlname.data,
  880.                 sqlda->sqlvar[index].sqlname.length);
  881.       } /* endfor */
  882.       fprintf(out_stream,"\n%s",row);
  883.  
  884.       /*_____________________________________________*/
  885.       /* Clear row buffer                            */
  886.       /*_____________________________________________*/
  887.       memset(row,' ',sizeof(row));
  888.       row[sizeof(row) +1] = '\0';
  889.  
  890.       /*_____________________________________________*/
  891.       /* Underline names                             */
  892.       /*_____________________________________________*/
  893.       row[sizeof(row) -1] = '\0';
  894.       for (index=0;index<max_num_flds ;index++ ) {
  895.          memset(temp,'-',field[index].max_width);
  896.          memcpy(&row[field[index].tab_pos], temp, field[index].max_width);
  897.       } /* endfor */
  898.       fprintf(out_stream,"\n%s",row);
  899.  
  900.       break;                                 /* end of action PRINT_COLUMNS   */
  901.  
  902.    case PRINT_SELECTED_ROW:
  903.       for (index=0;index<max_num_flds ;index++ ) {
  904.          /*_____________________________________________*/
  905.          /* Initialize                                  */
  906.          /*_____________________________________________*/
  907.          null_not_found = TRUE;
  908.          /*_____________________________________________*/
  909.          /* Is it null?                                 */
  910.          /*_____________________________________________*/
  911.          if (sqlda->sqlvar[index].sqltype & 1) {
  912.             if (* (sqlda->sqlvar[index].sqlind) == -1) {
  913.                sprintf(temp,"NULL");
  914.                null_not_found = FALSE;
  915.             } else {
  916.                if (* (sqlda->sqlvar[index].sqlind) != 0) {
  917.                   sprintf(err_msg,"\n Truncated field col = %d",index+1);
  918.                   rcd=FAILED;
  919.                   break;
  920.                } /* endif */
  921.             } /* endif */
  922.          } /* endif */
  923.          /*_____________________________________________*/
  924.          /* Is not null field                           */
  925.          /*_____________________________________________*/
  926.          if (null_not_found) {
  927.             switch (sqlda->sqlvar[index].sqltype) {
  928.             case SQL_TYP_INTEGER:
  929.             case SQL_TYP_NINTEGER:
  930.                sprintf(temp,"%ld", *(PLONG)sqlda->sqlvar[index].sqldata);
  931.                break;
  932.             case SQL_TYP_SMALL:
  933.             case SQL_TYP_NSMALL:
  934.                sprintf(temp,"%d", *(PSHORT)sqlda->sqlvar[index].sqldata);
  935.                break;
  936.             case SQL_TYP_DECIMAL:
  937.             case SQL_TYP_NDECIMAL:
  938.                len = sqlda->sqlvar[index].sqllen;
  939.                ptr = sqlda->sqlvar[index].sqldata;
  940.                sprintf(temp,"");
  941.                scale     = HIBYTE(len);
  942.                precision = LOBYTE(len);
  943.                y = (precision+2)/2;          /* total number of bytes         */
  944.                point = precision - scale;
  945.                bottom = *(ptr + y - 1) & 0x000F;    /* sign                    */
  946.                if ((bottom == 0x000D) || (bottom == 0x000B)) {
  947.                   strcat(temp,"-");
  948.                } /* endif */
  949.                output_blank = TRUE;
  950.                for (i=0;i<y ;i++ ) {
  951.                   top = *(ptr + i) & 0x00F0;
  952.                   top = (top >> 4);
  953.                   bottom = *(ptr + i) &0x000F;
  954.                   if (point-- == 0) {
  955.                      strcat(temp,".");
  956.                   } /* endif */
  957.  
  958.                   if (((output_blank) && (top != 0)) || (point <= 1)) {
  959.                      output_blank = FALSE;
  960.                   } /* endif */
  961.                   if (output_blank) {
  962.                      strcat(temp," ");
  963.                   } else {
  964.                      sprintf(temp1,"%d",top);
  965.                      strcat(temp,temp1);
  966.                   } /* endif */
  967.                   /*_____________________________________________*/
  968.                   /* Ignore bottom half of last half-byte        */
  969.                   /* because it's the sign.                      */
  970.                   /*_____________________________________________*/
  971.                   if (i < (y-1)) {
  972.                      /* sign half byte? */
  973.                      if (point-- == 0) {
  974.                         strcat(temp,".");
  975.                      } /* endif */
  976.                      if ((output_blank) && (bottom != 0) || (point <= 1)) {
  977.                         output_blank = FALSE;
  978.                      } /* endif */
  979.                      if (output_blank) {
  980.                         strcat(temp," ");
  981.                      } else {
  982.                         sprintf(temp1,"%d",bottom);
  983.                         strcat(temp,temp1);
  984.                      } /* endif */
  985.                   } /* endif */
  986.                } /* endfor */
  987.                if (scale == 0) {
  988.                   strcat(temp,".");
  989.                } /* endif */
  990.                break;
  991.             case SQL_TYP_FLOAT:
  992.             case SQL_TYP_NFLOAT:
  993.                sprintf(temp,"%e",*(float *)sqlda->sqlvar[index].sqldata);
  994.                break;
  995.             case SQL_TYP_CHAR:
  996.             case SQL_TYP_NCHAR:
  997.                strncpy(temp,
  998.                        sqlda->sqlvar[index].sqldata,
  999.                        sqlda->sqlvar[index].sqllen);
  1000.                temp[sqlda->sqlvar[index].sqllen] = '\0';       /* terminate   */
  1001.                break;
  1002.             case SQL_TYP_VARCHAR:
  1003.             case SQL_TYP_NVARCHAR:
  1004.             case SQL_TYP_LONG:
  1005.             case SQL_TYP_NLONG:
  1006.                strncpy(temp,
  1007.                        sqlda->sqlvar[index].sqldata + 2,
  1008.                        (SHORT)*sqlda->sqlvar[index].sqldata);
  1009.                temp[(SHORT)*sqlda->sqlvar[index].sqldata] = '\0'; /* terminate */
  1010.                break;
  1011.             case SQL_TYP_DATE:
  1012.             case SQL_TYP_NDATE:
  1013.                strncpy(temp,
  1014.                        sqlda->sqlvar[index].sqldata,10);
  1015.                temp[10] = '\0';                              /* terminate   */
  1016.                break;
  1017.             case SQL_TYP_TIME:
  1018.             case SQL_TYP_NTIME:
  1019.                strncpy(temp,
  1020.                        sqlda->sqlvar[index].sqldata,8);
  1021.                temp[8] = '\0';                              /* terminate   */
  1022.                break;
  1023.             case SQL_TYP_STAMP:
  1024.             case SQL_TYP_NSTAMP:
  1025.                strncpy(temp,
  1026.                        sqlda->sqlvar[index].sqldata,26);
  1027.                temp[26] = '\0';                             /* terminate   */
  1028.                break;
  1029.             case SQL_TYP_LSTR:
  1030.             case SQL_TYP_NLSTR:
  1031.                strncpy(temp,
  1032.                        sqlda->sqlvar[index].sqldata + 1,
  1033.                        sqlda->sqlvar[index].sqllen);
  1034.                temp[sqlda->sqlvar[index].sqllen] = '\0';         /* terminate */
  1035.                break;
  1036.             case SQL_TYP_CSTR:   /* null-terminated varying length string     */
  1037.             case SQL_TYP_NCSTR:
  1038.                sprintf(temp,"%s",sqlda->sqlvar[index].sqldata + 2);
  1039.                break;
  1040.             default:
  1041.                sprintf(err_msg,
  1042.                "\n Unknown type col = %d type = %d",
  1043.                index+1,sqlda->sqlvar[index].sqltype);
  1044.                rcd = FAILED;
  1045.                break;
  1046.             } /* endswitch */
  1047.          } /* endif */
  1048.  
  1049.          if (rcd == FAILED) {          /* break out of for loop               */
  1050.             break;
  1051.          } /* endif */
  1052.          if (strlen(temp) <= field[index].max_width) {
  1053.             memcpy(&row[field[index].tab_pos],temp,strlen(temp));
  1054.          } else {
  1055.             sprintf(err_msg,
  1056.             "\n Field too long col = %d value = %s",(index+1),temp);
  1057.             rcd = FAILED;
  1058.             break;
  1059.          } /* endif */
  1060.       } /* endfor */
  1061.  
  1062.       /*_____________________________________________*/
  1063.       /* Print selected row                          */
  1064.       /*_____________________________________________*/
  1065.       fputs("\n",out_stream);
  1066.       fputs(row,out_stream);
  1067.       break;
  1068.    } /* endswitch */
  1069.  
  1070.    return(rcd);
  1071.  
  1072. } /* end print_format_row */
  1073.  
  1074.  
  1075.  
  1076.  
  1077. /*___________________________________________________________________________*/
  1078. /* This procedure invokes an OS/2 program and passes it parameters           */
  1079. /*___________________________________________________________________________*/
  1080. SHORT dos_exec(PCHAR cmd_dos)
  1081. {
  1082.       /*_____________________________________________*/
  1083.       /* Execute the program                         */
  1084.       /*_____________________________________________*/
  1085.    api_rcd = DosExecPgm(object_name,      /* failing object if program fails  */
  1086.                   sizeof(object_name),    /* the object size                  */
  1087.                   0,                      /* sync. program execution          */
  1088.                   cmd_dos,                /* program name and parameters      */
  1089.                   NULL,                   /* inherit environment              */
  1090.                   &ExecResult,            /* termination reason code          */
  1091.                   cmd_dos);               /* program name                     */
  1092.    if (api_rcd) {
  1093.       sprintf(err_msg,
  1094.                "\n ERROR: DosExecPgm API call failed with %d return code",
  1095.                api_rcd);
  1096.       return(RECORD_DOS_EXEC_RESULTS);
  1097.    } /* endif */
  1098.       /*_____________________________________________*/
  1099.       /* Format the return codes                     */
  1100.       /*_____________________________________________*/
  1101.  
  1102.    switch (ExecResult.codeTerminate) {
  1103.    case 0:
  1104.       sprintf(err_msg,"\n Program completed with a return code of %d.",
  1105.                ExecResult.codeResult);
  1106.       api_rcd = ExecResult.codeResult;
  1107.       break;
  1108.    case 1:
  1109.       sprintf(err_msg,"\n Program terminated by hard error.");
  1110.       api_rcd = ExecResult.codeTerminate;
  1111.       break;
  1112.    case 2:
  1113.       sprintf(err_msg,"\n Program terminated by a TRAP.");
  1114.       api_rcd = ExecResult.codeTerminate;
  1115.       break;
  1116.    case 3:
  1117.       sprintf(err_msg,"\n Program terminated by a DosKillProcess.");
  1118.       api_rcd = ExecResult.codeTerminate;
  1119.       break;
  1120.    default:
  1121.       sprintf(err_msg,"\n Unknown Program termination code.");
  1122.       api_rcd = ExecResult.codeTerminate;
  1123.    } /* endswitch */
  1124.  
  1125.    return(RECORD_DOS_EXEC_RESULTS);
  1126.  
  1127. } /* end dos_exec */
  1128.  
  1129.  
  1130.  
  1131. /*___________________________________________________________________________*/
  1132. /* This procedure records the command results along with the elapsed         */
  1133. /* time of execution of a command.                                           */
  1134. /*___________________________________________________________________________*/
  1135. SHORT record_command_results(SHORT rcd)
  1136. {
  1137.    CHAR           display_msg[1000];         /* temporary buffer              */
  1138.    CHAR           msgbuf[512];               /* rcd explanation               */
  1139.    SHORT          index;                     /* for counting                  */
  1140.    CHAR           temp[20];                  /* char buffer                   */
  1141.    CHAR           *err_line;                 /* a line of error info.         */
  1142.  
  1143.    switch (rcd) {
  1144.    case RECORD_NOTHING:
  1145.       fprintf(out_stream,"\n\n");
  1146.       return(CONTINUE);
  1147.       break;
  1148.    case RECORD_DOS_EXEC_RESULTS:
  1149.       if (api_rcd == 0) {
  1150.          fprintf(out_stream,"%s",err_msg);
  1151.          fprintf(out_stream,
  1152.                   "\n OK.                       "
  1153.                   "Execution time = %10.4lf secs\n\n\n",
  1154.                   (double)event_time);
  1155.          return(CONTINUE);
  1156.       } else {
  1157.          fprintf(out_stream,"%s",err_msg);
  1158.          fprintf(out_stream,
  1159.                   "\n ERROR.                    "
  1160.                   "Execution time = %10.4lf secs\n\n\n",
  1161.                   (double)event_time);
  1162.          if (continue_on_error) {
  1163.             return(CONTINUE);
  1164.          } else {
  1165.             return(TERMINATE);
  1166.          } /* endif */
  1167.       } /* endif */
  1168.       break;
  1169.    case RECORD_SQLCA:
  1170.       if (SQLCODE == 0) {
  1171.          fprintf(out_stream,"%s",err_msg);
  1172.          fprintf(out_stream,
  1173.                   "\n OK. sql_rcd = %ld         "
  1174.                   "Execution time = %10.4lf secs\n\n\n",
  1175.                   SQLCODE,(double)event_time);
  1176.          return(CONTINUE);
  1177.       } else {
  1178.          if (SQLCODE > 0) {
  1179.             sprintf(display_msg,
  1180.             "\n WARNING, sql_code =%ld,    Execution time = %10.4lf secs",
  1181.             SQLCODE,(double)event_time);
  1182.          } else {
  1183.             sprintf(display_msg,
  1184.             "\n ERROR, sql_code = %ld\n",
  1185.             SQLCODE);
  1186.          } /* endif */
  1187.          /*_____________________________________________*/
  1188.          /* Retrieve error message                      */
  1189.          /*_____________________________________________*/
  1190.          rcd = sqlaintp(msgbuf,              /* buffer for msg text           */
  1191.                         512,                 /* buffer size                   */
  1192.                         79,                  /* line width                    */
  1193.                         &sqlca);             /* SQLCA                         */
  1194.  
  1195.          if (rcd < 0) {                      /* message retrieve error        */
  1196.             sprintf(msgbuf,"\n SQLAINTP ERROR, Return code = %d \n",rcd);
  1197.          } /* endif */
  1198.  
  1199.          err_line = strtok(msgbuf,"\n");
  1200.          while (err_line != NULL) {
  1201.             sprintf(display_msg,"%s\n %s",display_msg,err_line);
  1202.             err_line = strtok(NULL,"\n");
  1203.          } /* endwhile */
  1204.          strcat(display_msg,"\n\n ------ ADDITIONAL SQLCA Info --------");
  1205.          fputs(display_msg,out_stream);
  1206.  
  1207.          /*_____________________________________________*/
  1208.          /* Display SQLCA sqlerrmc                      */
  1209.          /*_____________________________________________*/
  1210.          if (sqlca.sqlerrml) {
  1211.             sqlca.sqlerrmc[sqlca.sqlerrml] = '\0';    /* NULL terminate       */
  1212.             while (sqlca.sqlerrml--) {
  1213.                if (sqlca.sqlerrmc[sqlca.sqlerrml] == 0xFF) {   /* remove FFs  */
  1214.                   sqlca.sqlerrmc[sqlca.sqlerrml] = ' ';
  1215.                } /* endif */
  1216.             } /* endwhile */
  1217.             fprintf(out_stream,"\n SQLERRMC's:  %s",sqlca.sqlerrmc);
  1218.          } /* endif */
  1219.  
  1220.          /*_____________________________________________*/
  1221.          /* Display SQLCA sqlerrp                       */
  1222.          /*_____________________________________________*/
  1223.          sprintf(display_msg,"\n SQLERRP: ");
  1224.          for (index=0;index<8 ;index++ ) {
  1225.             sprintf(temp,"%c",sqlca.sqlerrp[index]);
  1226.             strcat(display_msg,temp);
  1227.          } /* endfor */
  1228.          fputs(display_msg,out_stream);
  1229.  
  1230.          /*_____________________________________________*/
  1231.          /* Display SQLCA sqlerrd                       */
  1232.          /*_____________________________________________*/
  1233.          sprintf(display_msg,"\n SQLERRD: ");
  1234.          for (index=0;index<6 ;index++ ) {
  1235.             sprintf(temp,"%10ld",sqlca.sqlerrd[index]);
  1236.             strcat(display_msg,temp);
  1237.          } /* endfor */
  1238.          fputs(display_msg,out_stream);
  1239.  
  1240.          /*_____________________________________________*/
  1241.          /* Display SQLCA warnings                      */
  1242.          /*_____________________________________________*/
  1243.          sprintf(display_msg,"\n Warning Indicators: ");
  1244.          for (index=0;index<5 ;index++ ) {
  1245.             sprintf(temp,"%c",sqlca.sqlwarn[index]);
  1246.             strcat(display_msg,temp);
  1247.          } /* endfor */
  1248.          fprintf(out_stream,"%s\n\n\n",temp);
  1249.  
  1250.          if (continue_on_error) {
  1251.             return(CONTINUE);
  1252.          } else {
  1253.             return(TERMINATE);
  1254.          } /* endif */
  1255.  
  1256.       } /* endif */
  1257.       break;
  1258.    case RECORD_API_RCD:
  1259.       if (api_rcd == 0) {
  1260.          fprintf(out_stream,
  1261.          "\n OF, api_rcd = %ld,         "
  1262.          " Execution time = %10.4lf secs\n\n\n",
  1263.          api_rcd,(double)event_time);
  1264.          return(CONTINUE);
  1265.       } else {
  1266.          fprintf(out_stream,
  1267.          "\n API for command %s failed with "
  1268.          "a return code of %d.\n\n\n",
  1269.          parms.cmd_name,api_rcd);
  1270.       } /* endif */
  1271.       if (continue_on_error) {
  1272.          return(CONTINUE);
  1273.       } else {
  1274.          return(TERMINATE);
  1275.       } /* endif */
  1276.       break;
  1277.    case RECORD_ERR_MSG:
  1278.       fprintf(out_stream," %s\n\n\n", err_msg);
  1279.       return(TERMINATE);
  1280.       break;
  1281.    } /* endswitch */
  1282. } /* end record_command_results */
  1283.  
  1284.  
  1285.  
  1286. /*___________________________________________________________________________*/
  1287. /* Dispatch Database Administration Command Handler                          */
  1288. /*___________________________________________________________________________*/
  1289. SHORT dba_exec(PCHAR parm_buf)
  1290. {
  1291.    /*_____________________________________________*/
  1292.    /* Display SQLCA sqlerrd                       */
  1293.    /*_____________________________________________*/
  1294.    switch (parms.cmd_num) {
  1295.          /*_____________________________________________*/
  1296.          /* Environment Services                        */
  1297.          /*_____________________________________________*/
  1298.    case CMD_DBA_STARTUSE        : rcd = dba_startuse(parm_buf);      break;
  1299.    case CMD_DBA_STOPUSE         : rcd = dba_stopuse();               break;
  1300.    default: RECORD_NOTHING;                                          break;
  1301.    } /* endswitch */
  1302.  
  1303.    return(rcd);
  1304.  
  1305. } /* end dba_exec */
  1306.  
  1307.  
  1308.  
  1309. /*___________________________________________________________________________*/
  1310. /* execute the STARTUSE DBA function                                         */
  1311. /* FORMAT: EXEC DBA: STARTUSE database_name [S/X]                            */
  1312. /*___________________________________________________________________________*/
  1313. SHORT dba_startuse(PCHAR parm_str)
  1314. {
  1315.    BYTE  database_name[9];                   /* Database name,null terminated */
  1316.    CHAR  share_mode;                         /* Share mode for STARTUSE       */
  1317.    /*_____________________________________________*/
  1318.    /* Get the parm strings                        */
  1319.    /*_____________________________________________*/
  1320.    if (sscanf(parm_str, " %8s %c ", database_name, &share_mode)
  1321.             != parms.num_parms) {
  1322.       sprintf(err_msg, "\nSYNTAX ERROR: invalid parameters.");
  1323.       return(RECORD_ERR_MSG);
  1324.    } /* endif */
  1325.  
  1326.    /*_____________________________________________*/
  1327.    /* call the START USING DB API                 */
  1328.    /*_____________________________________________*/
  1329.    sqlestrd(database_name,share_mode,&sqlca);
  1330.  
  1331.    if (SQLCODE == RESTART) {
  1332.    /*_____________________________________________*/
  1333.    /* call the RESTART DB API                     */
  1334.    /*_____________________________________________*/
  1335.    sqlerest(database_name,&sqlca);
  1336.    } /* endif */
  1337.  
  1338.    if (SQLCODE != 0) {
  1339.       return(RECORD_SQLCA);
  1340.    } else {
  1341.       /*_____________________________________________*/
  1342.       /* call the START USING DB API (again)         */
  1343.       /*_____________________________________________*/
  1344.       sqlestrd(database_name,share_mode,&sqlca);
  1345.    } /* endif */
  1346.  
  1347.    if (SQLCODE != 0) {
  1348.       return(RECORD_SQLCA);
  1349.    } /* endif */
  1350.  
  1351.    sqleisig(&sqlca);                      /* handle CTRL-BRK signal handler */
  1352.  
  1353.    return(RECORD_SQLCA);
  1354.  
  1355. } /* end dba_startuse */
  1356.  
  1357.  
  1358.  
  1359. /*___________________________________________________________________________*/
  1360. /* execute the STOPUSE DBA function                                          */
  1361. /* FORMAT: EXEC DBA: STOPUSE                                                 */
  1362. /*___________________________________________________________________________*/
  1363. SHORT dba_stopuse(VOID)
  1364. {
  1365.    /*_____________________________________________*/
  1366.    /* Call the STOP USING DB API                  */
  1367.    /*_____________________________________________*/
  1368.    sqlestpd(&sqlca);
  1369.    return(RECORD_SQLCA);
  1370.  
  1371. } /* end dba_stopuse */
  1372.  
  1373.