sql 실행기를 클라이언트로 구현을 하려고 합니다 서버는 ESQLC를 사용해서 하려고 하는데 문제는 select시 fetchl되어지는 컬럼수가 다이나믹하다는겁니다 어떻게 하면 문제를 해결 할수 있을까요 ?
ESQLC를 잘 몰라 doc를 좀 찾아 봤습니다. esqlc 메뉴얼에 있는 dynamic sql 에 있는 method 4를 참조하면 될 것 같습니다. 설명에는 컬럼 갯수를 모를경우에 적용할 수 있는 방법이라고 나와 있긴 하네요.
예, 저도 어제 보았는데 예제가 너무 난해하네요 감사합니다
저만 어려웠던게 아니군요...^^; 이런거 하나 완벽하게 쓸만한 예제로 나오면 더 짜집기 대마왕 한 번 해볼만 할텐데 하는 소망이....ㅋㅋ . 인터넷 어딘가엔 완벽한 코드가 있겠지 소망해 봅니다.
소스화일 구했읍니다, 되더군요
Embedded SQL/C SAMPLE PROGRAMS The following sample programs demonstrate features of Embedded SQL/C and can be used as models for your own programs.
Embedded SQL/C Sample Programs
The following sample programs demonstrate features of Client-Library and can be used as models for your own programs.
************************************************************************* Open Client and Open Server Program Disclaimer
The Open Client and Open Servers applications distributed on the WWW have been created to provide customers with ideas and help working with Sybase connectivity libraries.
Please read this disclaimer before using the code:
THIS CODE IS BEING DISTRIBUTED FREE OF CHARGE. IT IS NOT A SYBASE PRODUCT, IS NOT SUPPORTED BY SYBASE AND IS PROVIDED "AS-IS" WITHOUT WARRANTY OF ANY KIND. SYBASE DISCLAIMS ALL WARRANTIES OR CONDITIONS, EITHER EXPRESS OR IMPLIED, INCLUDING WITHOUT LIMITATION ANY IMPLIED WARRANTIES OF MERCHANTABILITY, MERCHANTABLE QUALITY, NONINFRINGEMENT AND FITNESS FOR A PARTICULAR PURPOSE (WHETHER ARISING BY STATUTE OR IN LAW OR AS A RESULT OF A COURSE OF DEALING OR USAGE OF TRADE). IN NO EVENT SHALL SYBASE BE LIABLE FOR LOSS OF PROFITS OR LOSS OF DATA OR ANY DAMAGES WHATSOEVER INCLUDING WITHOUT LIMITATION DIRECT, INDIRECT, INCIDENTAL, CONSEQUENTIAL OR SPECIAL DAMAGES, EVEN IF SYBASE HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGES.
*************************************************************************
The following is a list of all the Client-Library programs in this document and a brief description of what each program does. A makefile and a header file (sybsqlex.h) for these programs is included at the end of this document.
Use your browser's search tool to locate the program you wish to see.
Notes: - Most of these programs require the 'pubs2' database. - A program may have an associated readme file and a isql script file depending on the requirement (check list below). - Unless otherwise stated in the program description or the program's readme file, all programs can be executed by simply typing the name of the executable.
Program name Description Other files ************ *********** ***********
indicator Retrieves data using a indicator.sql cursor. Makes use of in- dicator variables to denote NULLS.
arrays Selects multiple rows of data from a single select into a host array instead of using cursors. May be used to improve performance.
arrays_cur Uses cursors and arrays - arrays_cur.readme fetches data in batches of 'x' rows until all rows have been fetched. Uses a workaround for sqlca.sqlerrd[2].
stored_proc Uses a stored procedure to return multiple rows into host variables using arrays.
sqlda Demonstrates the use of the new SQLDA structure in ESQL 11.x.
date_convert Converts and displays a given date in the required format.
descriptor Uses system descriptors to retrieve the data, type, and other information about the returned data.
text_image Makes use of mixed mode ct-lib text_image.sql calls to handle text/image data. Note that in System 11, ESQL will support text/image types.
dynamic1 Demonstrates the use of Dynamic SQL Method 1 - EXECUTE IMMEDIATE.
dynamic2 Demonstrates the use of Dynamic SQL Method 2 using PREPARE and EXECUTE.
dynamic3 Demonstrates the use of dynamic3.sql Dynamic SQL Method 3- using PREPARE. It also shows how rows retrieved by the cursor can be UPDATED using the WHERE CURRENT OF clause.
dynamic4 Demonstrates the use of dynamic Dynamic SQL Method 4 to handle varying list select statements.
************************************************************************* indicator.cp
/* Program name : indicator.cp ** ** Description : This program uses cursors to retrieve data from a table that ** contains data of various datatypes. It displays the data if ** any, or else uses indicator variables to denote a NULL. ** Note: a -1 indicates NULL, and 0 NOT NULL. ** ** Script file : indicator.sql ** */
#include <stdio.h> #include <string.h> #include "sybsqlex.h"
/* Declare the SQLCA */ EXEC SQL INCLUDE sqlca;
/* ** Forward declarations of the error and message handlers and ** other subroutines called from main(). */ void error_handler(); void warning_handler();
int main() { EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_CHAR char_col[10], num_col[10], dec_col[30] ; CS_CHAR int_col[10], flt_col[30] ; CS_SMALLINT char_indic, int_indic, flt_indic, num_indic, dec_indic; EXEC SQL END DECLARE SECTION ;
EXEC SQL WHENEVER SQLERROR CALL error_handler(); EXEC SQL WHENEVER NOT FOUND STOP ; EXEC SQL WHENEVER SQLWARNING CALL warning_handler();
/* ** Copy the user name and password defined in sybsqlex.h to ** the variables declared for them in the declare section. */ strcpy(username, USER); strcpy(password, PASSWORD);
EXEC SQL CONNECT :username IDENTIFIED BY :password ; EXEC SQL USE tempdb ; EXEC SQL DECLARE sel_cursor CURSOR FOR select * from all_types ; EXEC SQL OPEN sel_cursor ; printf("Data \t\t Null/Not null \n") ; printf("----------------------------------- \n") ; for ( ;; ) { strcpy(char_col,"NULL"); strcpy(int_col,"NULL"); strcpy(flt_col,"NULL"); strcpy(num_col,"NULL"); strcpy(dec_col,"NULL"); if ( sqlca.sqlcode == 100 ) { printf("No more results. \n"); break ; } EXEC SQL FETCH sel_cursor INTO :char_col :char_indic, :int_col :int_indic , :flt_col :flt_indic , :num_col :num_indic , :dec_col :dec_indic ;
printf("%-20s %d\n",char_col, char_indic ); printf("%-20s %d\n",int_col , int_indic ); printf("%-20s %d\n",flt_col , flt_indic ); printf("%-20s %d\n",num_col , num_indic ); printf("%-20s %d\n",dec_col , dec_indic ); printf("\n \n"); } EXEC SQL DISCONNECT ALL; exit(0); }
/* ** void error_handler() ** ** Displays error codes and numbers from the SQLCA and exits with ** an ERREXIT status. */ void error_handler() { fprintf(stderr, "\n** SQLCODE=(%d)", sqlca.sqlcode);
if (sqlca.sqlerrm.sqlerrml) { fprintf(stderr, "\n** Error Message: "); fprintf(stderr, "\n** %s", sqlca.sqlerrm.sqlerrmc); }
fprintf(stderr, "\n\n");
exit(ERREXIT); }
/* ** void warning_handler() ** ** Displays warning messages. */ void warning_handler() {
if (sqlca.sqlwarn[1] == 'W') { fprintf(stderr, "\n** Data truncated.\n"); }
if (sqlca.sqlwarn[3] == 'W') { fprintf(stderr, "\n** Insufficient host variables to store results.\n"); } return; }
************************************************************************* indicator.sql
use tempdb go if exists ( select 1 from sysobjects where name = 'all_types' and type = 'U' ) drop table all_types go create table all_types ( char_col char(10) null, int_col int null, flt_col float null, num_col numeric(8,2) null, dec_col decimal(8,2) null ) go
insert into all_types values ( 'hello', 1, 12345.56, 456.78, 12345.56 ) go insert into all_types values ( null , 2, 12345.56, 456.78, 9999.99 ) go insert into all_types values ( 'world' , null, 12345.56, 456.78, 8768.24 ) go insert into all_types values ( 'hello' , 3, null, 456.78, 3246.99 ) go insert into all_types values ( 'world' , 4, 345.12, null, 349.56 ) go insert into all_types values ( 'hello' , 5, 12348.92, 34.89, null ) go
************************************************************************* arrays.cp
/* Program name : arrays.cp ** ** Description : This program selects multiple rows of data for a single ** select using host arrays rather than cursors. Using ** arrays is typically faster than using cursors. The program ** also uses the variable sqlca.sqlerrd[2], which contains ** the number of rows affected by the previous SQL statement. ** ** Note : This example is based on the assumption that the 'publishers' ** table has not been changed. Since the array size has been ** defined as 3 (see the variable declaration section below), ** the SELECT query can only return 3 rows. Change the size of ** the array if you expect more rows from your query. ** ** References : Open Client Embedded SQL/C Programmer's Guide - chapter on ** Using Host Variables, sub-heading 'Using Arrays'. */
#include <stdio.h> #include "sybsqlex.h"
EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_CHAR pub_id[5][10], pub_name[5][30], pub_city[5][30]; CS_CHAR pub_state[5][10] ; EXEC SQL END DECLARE SECTION;
int main() { int i=0 ;
EXEC SQL WHENEVER SQLERROR CALL error_handler(); EXEC SQL WHENEVER SQLWARNING CALL warning_handler(); EXEC SQL WHENEVER NOT FOUND CONTINUE;
/* ** Copy the user name and password defined in sybsqlex.h to ** the variables declared for them in the declare section. */
strcpy(username, USER); strcpy(password, PASSWORD);
EXEC SQL CONNECT :username IDENTIFIED BY :password ; EXEC SQL USE pubs2 ; /* Now, issue the query and store the results in host arrays */ EXEC SQL SELECT pub_id , pub_name, city, state INTO :pub_id, :pub_name, :pub_city, :pub_state FROM publishers ;
for ( i = 0 ; i < sqlca.sqlerrd[2] ; i++ ) { printf("Pub Id : %s\n", pub_id[i]) ; printf("Pub Name : %s\n", pub_name[i]) ; printf("Pub City : %s\n", pub_city[i]) ; printf("Pub State : %s\n", pub_state[i]); printf("\n\n"); } EXEC SQL DISCONNECT ALL; exit(0); }
************************************************************************* arrays_cur
/* Program name : arrays_cur.cp ** ** Description : The program uses cursors to fetch data into host arrays in ** batches. This method is useful when you don't know ** how many rows will be retrieved and do not want to ** allocate large amounts of memory to the arrays. ** This program fetches rows in batches of 5. Since there ** is no feature as yet that returns the number of rows ** affected by a cursor fetch (see arrays_cur.readme), you ** need to use a routine to return the number of rows fetched ** by the previous fetch statement. ** ** Notes: ** - sqlca.sqlerrd[2] does not contain this information. ** - The routine 'get_rowsread' is specific to 11.x. ** See the arrays_cur.readme file for the equivalent ** 10.x routine. ** */
/* Global def */ long SQLCODE;
EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_SMALLINT indic1[5], indic2[5], indic3[5]; CS_CHAR title_id[5][25], type[5][20], price[5][20] ; EXEC SQL END DECLARE SECTION;
/* ** Forward declarations of the error and message handlers and ** other subroutines called from main(). */ void error_handler(); void warning_handler(); void do_print_data(); int get_rowsread();
int main() { int i=0, rows = 0;
EXEC SQL WHENEVER SQLERROR CALl error_handler(); EXEC SQL WHENEVER SQLWARNING CALL warning_handler(); EXEC SQL WHENEVER NOT FOUND STOP;
EXEC SQL CONNECT :username IDENTIFIED BY :password ; EXEC SQL USE pubs2 ; EXEC SQL DECLARE sel_cursor CURSOR FOR SELECT title_id, type, price FROM titles ; EXEC SQL OPEN sel_cursor;
for ( ;; ) { EXEC SQL FETCH sel_cursor INTO :title_id :indic1, :type :indic2, :price :indic3; if ( sqlca.sqlcode == 100 ) break ; /* Workaround to get the number of rows fetched by the ** last cursor FETCH. */ rows = get_rowsread(); printf("Printing batch of %d records .. press RETURN \n", rows); getchar(); do_print_data(rows); } EXEC SQL CLOSE sel_cursor; EXEC SQL DISCONNECT ALL; exit(0); }
/* ** void do_print_data(rows) ** ** Displays the data fetched by the cursor. Also checks the value in the ** indicator variable and subsitutes the word "NULL" for null values. ** */ void do_print_data(rows) int rows ; { int i = 0;
printf("Title id Type Price \n"); printf("-----------------------------------------\n"); for ( i = 0 ; i< rows ; i++ ) {
if ( indic1[i] == -1 ) strcpy(title_id[i],"NULL"); if ( indic2[i] == -1 ) strcpy(type[i],"NULL"); if ( indic3[i] == -1 ) strcpy(price[i],"NULL");
printf("%-15s %-15s %10s\n",title_id[i], type[i], price[i] ); } }
/* ** int get_rowsread() ** ** retrieves the number of rows affected by the last cursor fetch from ** the sql handle. ** */ int get_rowsread() { _SQL_CT_HANDLES *_sql;
_sqlinitctx(&_sql, CS_VERSION_110, CS_TRUE, (SQLCA *)NULL, &SQLCODE, (CS_CHAR *)NULL); if ( _sql != (_SQL_CT_HANDLES *) NULL) return(_sql->rowsread); return(CS_FAIL); }
************************************************************************* arrays_cur.readme
Description: The following notes explain how sqlca.sqlerrd[2] works with regular selects and cursors. Normally, sqlca.sqlerrd[2] contains the number of rows affected by the last command. This variable is particularly useful when you use host arrays but do not know beforehand how many rows to expect.
However, you cannot use this variable with fetches from cursors, though this feature has been requested. This readme explains why you cannot use sqlca.sqlerrd[2] with cursors and a workaround for the problem. CTlib sets the sqlca.sqlerrd[2] variable when it receives a TDS-DONE token from the server. This token contains a 'count' field indicating how many rows were affected by the last command. However, cursor fetches do not cause the server to send a TDS-DONE token -- at least not until the final row of the cursor result set has been fetched -- and until that last row neither the server nor the client knows how many total rows there are going to be.
However, sqlca.sqlerrd[2] is not set for a FETCH into host-variable arrays. This is not currently supported. The last parameter to the ct_fetch() call is a (* CS_INT), into which ct_fetch will place the number of rows fetched on a cursor fetch. In the current ESQL generated code, that variable is _sql->rowsread; an element of the _SQL_CT_HANDLES structure defined in $SYBASE/include/sybhesql.h
Workaround: *********** The _sql pointer is initialized by every call to _sqlinitctx() -- this function can be found in sybtesql.h -- and is set to the same address every time (unless you are running in a multi-threaded environment, in which case it is set to a different address for each thread). The workaround for determining the number of rows fetched on a single cursor fetch is to declare your own _SQL_CT_HANDLES variable, initialize it and use it. Wrap these workarounds in MACROs in your code so that it is easy to change when the ESQL product changes. ************************************************************************* Code for 10.x - 'get_rowsread':
int get_rowsread() { static _SQL_CT_HANDLES *mysqlhandle = (_SQL_CT_HANDLES *) NULL; if (mysqlhandle == (_SQL_CT_HANDLES *) NULL) { /* first call, initialize the pointer */ _sqlinitctx(&mysqlhandle, CS_VERSION_100, _SQL_DIAG_TYPE, (SQLCA *) NULL, (long *) NULL, (char *) NULL); } return(mysqlhandle->rowsread); }
************************************************************************* Code for 11.x - 'get_rowsread':
/*Gloabl def */ long SQLCODE; .......... int get_rowsread() { _SQL_CT_HANDLES *_sql;
_sqlinitctx(&_sql, CS_VERSION_110, CS_TRUE, (SQLCA *)NULL, &SQLCODE, (CS_CHAR *)NULL); if (_sql != (_SQL_CT_HANDLES *) NULL) return(_sql->rowsread); return(CS_FAIL);
************************************************************************* stored_proc.cp
/* Program name : stored_proc.cp ** ** Description : In this program we use a stored procedure to return ** mutliple rows into host variables. Note that this is ** is possible only if the variables are arrays or a ** cursor is used. ** This example uses host arrays. ** */
/* Declare the SQLCA */ EXEC SQL INCLUDE SQLCA;
int main() { EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_CHAR pub_id[4][5], pub_name[4][40], stmt[100] ; CS_CHAR city[4][15], state[4][3]; CS_INT ret_status; EXEC SQL END DECLARE SECTION ;
int i = 0;
EXEC SQL CONNECT :username IDENTIFIED BY :password; EXEC SQL USE pubs2 ; EXEC SQL set chained off;
strcpy(stmt,"create proc testproc as select * from publishers return "); EXEC SQL EXECUTE IMMEDIATE :stmt; EXEC SQL EXEC :ret_status = testproc INTO :pub_id, :pub_name, :city, :state;
printf("Pub Id Publisher Name City State \n"); printf("\n----- ----------------------- ------------ -----\n");
for ( i = 0 ; i < sqlca.sqlerrd[2] ; i++ ) { printf("%-8s", pub_id[i]) ; printf("%-25s", pub_name[i]) ; printf("%-12s", city[i]) ; printf("%-10s\n", state[i]) ; } printf("\n(%d rows affected, return status = %d)\n", sqlca.sqlerrd[2], ret_status);
/* Now, do the cleanup - drop the stored procedure */ strcpy(stmt,"drop proc testproc"); EXEC SQL EXECUTE IMMEDIATE :stmt;
EXEC SQL DISCONNECT ALL; exit(0); }
************************************************************************* sqlda.cp
/* Program name: sqlda_example.cp ** ** Description : This program demonstrates the use of the new SQLDA structure ** in ESQL 11.x. ** */
/* Declare the sqlca and sqlda structures */ EXEC SQL INCLUDE sqlca; EXEC SQL INCLUDE sqlda;
EXEC SQL BEGIN DECLARE SECTION; /* storage for the login name and password */ char username[30], password[30]; char cmd_buf[100], char_var[10][25]; float float_var[10]; int int_var[10] ; EXEC SQL END DECLARE SECTION;
int main() {
int i, j, k, l; SQLDA *in_sqlda, *out_sqlda;
EXEC SQL CONNECT :username IDENTIFIED BY :password;
EXEC SQL USE pubs2;
printf("Please enter a select statement in the form: "); printf("select column_list from dbname.owner.table "); printf("where colname =( or any valid relational operator ) ? .. \n"); fflush(stdin); gets(cmd_buf); /* Allocate SQLDAs */
/* SQLDA for describing the input parameters */ in_sqlda = (SQLDA *)malloc(SYB_SQLDA_SIZE(100)); in_sqlda->sd_sqln = 100;
/* SQLDA for describing the output parameters */ out_sqlda = (SQLDA *)malloc(SYB_SQLDA_SIZE(100)); out_sqlda->sd_sqln = 100;
/* Prepare the dynamic statement */ EXEC SQL PREPARE stmt from :cmd_buf;
/* Declare the cursor */ EXEC SQL DECLARE cursor1 CURSOR FOR stmt;
/* Get a description of the user inputs and place the appropriate ** inputs into the descriptor. */
EXEC SQL DESCRIBE INPUT stmt USING DESCRIPTOR in_sqlda;
i=0; j= 0; k=0; l=0; for (i = 0; i < in_sqlda->sd_sqld; i++) { switch ( in_sqlda->sd_column[i].sd_datafmt.datatype ) { case CS_CHAR_TYPE: case CS_DATETIME_TYPE: case CS_DATETIME4_TYPE: printf("CHAR/DATETIME TYPE! \n"); printf("Enter value for %d parameter: ",i+1); gets(char_var[j]); in_sqlda->sd_column[i].sd_sqldata = char_var[j]; in_sqlda->sd_column[i].sd_sqllen = strlen(char_var[j]); j++; break;
case CS_SMALLINT_TYPE: case CS_INT_TYPE: case CS_BIT_TYPE: printf("INT/SMALLINT/BIT TYPE! \n"); printf("Enter value for %d parameter: ",i+1); scanf("%d",&int_var[k]); in_sqlda->sd_column[i].sd_sqldata = &int_var[k]; in_sqlda->sd_column[i].sd_sqllen = sizeof(int_var); k++; break; case CS_FLOAT_TYPE: case CS_MONEY_TYPE: printf("FLOAT/MONEY TYPE! \n"); printf("Enter value for %d parameter: ",i+1); scanf("%f",&float_var[l]); in_sqlda->sd_column[l].sd_sqldata = &float_var[l]; in_sqlda->sd_column[l].sd_sqllen = sizeof(float_var); l++; break;
case CS_TEXT_TYPE: case CS_IMAGE_TYPE: printf("TEXT/IMAGE TYPE! "); printf("Both these types are invalid in "); printf("WHERE clauses or in dynamic SQL. \n"); break;
default: printf("Unknown type! Exiting .. \n"); break; } }
/* Open the cursor using the defined descriptor */ EXEC SQL OPEN cursor1 USING DESCRIPTOR in_sqlda;
/* Set the output SQLDA to point to output variables before the fetch */ EXEC SQL DESCRIBE OUTPUT stmt USING DESCRIPTOR out_sqlda;
j=k=l=0; for ( i = 0; i < out_sqlda->sd_sqld; i++ ) { switch ( out_sqlda->sd_column[i].sd_datafmt.datatype ) { case CS_INT_TYPE: case CS_SMALLINT_TYPE: out_sqlda->sd_column[i].sd_sqldata = &int_var[k]; out_sqlda->sd_column[i].sd_datafmt.format = CS_FMT_UNUSED; break;
case CS_FLOAT_TYPE: case CS_MONEY_TYPE: out_sqlda->sd_column[i].sd_sqldata = &float_var[l]; out_sqlda->sd_column[i].sd_datafmt.format = CS_FMT_UNUSED; break; case CS_CHAR_TYPE: default: out_sqlda->sd_column[i].sd_sqldata = char_var[j]; out_sqlda->sd_column[i].sd_datafmt.format = CS_FMT_NULLTERM;
break;
}; }
/* Fetch the results */ EXEC SQL FETCH cursor1 INTO DESCRIPTOR out_sqlda;
/* Process the results */
for ( i = 0; i < out_sqlda->sd_sqld; i++ ) { switch ( out_sqlda->sd_column[i].sd_datafmt.datatype ) { case CS_INT_TYPE: case CS_SMALLINT_TYPE: printf("%d\n",out_sqlda->sd_column[i].sd_sqldata); break;
case CS_FLOAT_TYPE: case CS_MONEY_TYPE: printf("%f\n",out_sqlda->sd_column[i].sd_sqldata); break;
case CS_CHAR_TYPE: default : printf("returned char data! \n"); printf("%s\n",out_sqlda->sd_column[i].sd_sqldata); break; }; }
EXEC SQL CLOSE cursor1 ; EXEC SQL DEALLOCATE CURSOR cursor1; EXEC SQL DISCONNECT ALL; exit(0); }
************************************************************************* date_convert.cp
} /* Program name : date_convert.cp ** ** Description : This program shows how to display a given date in the ** required format using the Transact-SQL 'convert' statement. ** */
int main() { EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_CHAR today[10] ; EXEC SQL END DECLARE SECTION;
EXEC SQL CONNECT :username identified by :password ; /* Convert today's date to the form mm/dd/yy . ** Refer to the Transact-SQL User's Guide for a list ** of the various date formats available. */ EXEC SQL SELECT convert(char(8),getdate(),1) INTO :today ; printf("\n The date in (mm/dd/yy) format is: %s\n\n",today); EXEC SQL DISCONNECT ALL; exit(0); }
************************************************************************* descriptor.cp
/* Program name : descriptor.cp ** ** Description : This program uses system descriptors to retrieve information ** about data retrieved from a given SELECT statement. It uses ** Method 4 of Dynamic SQL (see also example dynamic4) to ** 'PREPARE' a select list input by the user. It then uses system ** descriptors to fetch the number of columns retrieved by the ** select list, the type of data and the data itself. ** This program retrieves data of all types into a character ** buffer, but is is easy to check the type of data and store them ** in appropriate host variables (as shown in example dynamic4 ). ** */
/* Decalre the SQLCA */ EXEC SQL INCLUDE SQLCA;
int main() { EXEC SQL BEGIN DECLARE SECTION; /* storage for the login name and password */ CS_CHAR username[30], password[30]; CS_CHAR charbuff[50], colname[33], stmt[50] ; int numcols,i, coltype ,len; EXEC SQL END DECLARE SECTION ;
EXEC SQL WHENEVER SQLERROR CALL error_handler(); EXEC SQL WHENEVER SQLWARNING CALL warning_handler(); EXEC SQL WHENEVER NOT FOUND STOP ;
strcpy(username, USER); strcpy(password, PASSWORD); EXEC SQL CONNECT :username IDENTIFIED BY :password;
/* Set the database context to the one to be used */ EXEC SQL USE pubs2 ;
/* Allocate a descriptor */ EXEC SQL ALLOCATE DESCRIPTOR big_desc WITH max 256;
/* Now, accept a dynamic query from the user */ printf("Please enter a SQL select statement: "); fflush(stdin); gets(stmt); EXEC SQL PREPARE desc1 FROM :stmt ;
/* Declare a cursor for the dynamic sql statement, open the cursor ** and store the row information from the descriptor in host variables. */ EXEC SQL DECLARE sel_cursor CURSOR FOR desc1 ; EXEC SQL OPEN sel_cursor USING SQL DESCRIPTOR big_desc ; printf("NAME DATA LENGTH\n"); printf("---- ----- ------\n");
while (( sqlca.sqlcode != 100 ) && ( sqlca.sqlcode >= 0 )) { EXEC SQL FETCH sel_cursor INTO SQL DESCRIPTOR big_desc ; EXEC SQL GET DESCRIPTOR big_desc :numcols = count ; for ( i = 1 ; i <= numcols ; i++ ) { EXEC SQL GET DESCRIPTOR big_desc VALUE :i :coltype = TYPE; EXEC SQL GET DESCRIPTOR big_desc VALUE :i :colname = NAME; EXEC SQL GET DESCRIPTOR big_desc VALUE :i :charbuff = DATA ; EXEC SQL GET DESCRIPTOR big_desc VALUE :i :len = LENGTH ; printf("%-20s %-20s \t%d\n", colname, charbuff, len); }
printf("\n-----------------------------------------------------------\n"); }
/* Clean up the cursor, the descriptor and the prepared statament */ EXEC SQL CLOSE sel_cursor ; EXEC SQL DEALLOCATE PREPARE desc1 ; EXEC SQL DEALLOCATE DESCRIPTOR big_desc ;
EXEC SQL DISCONNECT ALL; exit(0);
}
/* ** void error_handler() ** ** Displays error codes and numbers from the SQLCA and exits with ** an ERREXIT status. */ void error_handler() {
fprintf(stderr, "\n** SQLCODE=(%d)", sqlca.sqlcode);
exit(ERREXIT);
************************************************************************* short_text.sql
use tempdb go if exists ( select 1 from sysobjects where name = 'text_tab' and type = 'U' ) drop table text_tab go create table text_tab ( text_col text null) go
************************************************************************* text_image.cp
/* Program name : text_image.cp ** ** Description : Inserting text and image data using host variables of ** types CS_TEXT and CS_IMAGE. ** ** Notes : This is a new feature in 11.x which allows you to use ** host variables of type CS_TEXT and CS_IMAGE in insert ** or update statements. ** Prior to this release, you needed to use mixed-mode ** Client-Library programming to handle text or image data, or ** else use Dynamic SQL, which had a limit of 64 k bytes. ** The size of the text or image data that can now be sent is ** limited only by memory or the maximum size allowed for ** text and image data by the server. However, sending large ** data this way slows performance. ** ** Script file : text_image.sql ** ** Notes : Be sure to compile using the '-y' precompiler flag. ** ** */
int main() { int i=0;
EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_TEXT text_var[10000]; CS_IMAGE image_var[10000]; EXEC SQL END DECLARE SECTION;
/* Connect to the server and specify the database to use */ EXEC SQL CONNECT :username IDENTIFIED BY :password;
EXEC SQL USE tempdb ;
/* Put something interesting in the variables. */ for (i=0; i< 10000; i++ ) { text_var[i] = 'a'; image_var[i] = '@'; }
EXEC SQL INSERT text_tab VALUES(:text_var, :image_var); if ( sqlca.sqlcode == 0 ) { printf("Row successfully inserted! \n"); EXEC SQL COMMIT WORK ; }
************************************************************************* text_image.sql
use tempdb go
if exists ( select 1 from sysobjects where name = 'text_tab' and type = 'U' ) drop table text_tab go
create table text_tab ( text_col text null, image_col image null) go
************************************************************************* dynamic1
/* Program name : dynamic1.cp ** ** ** Description : This program demonstrates the use of Dynamic SQL Method 1. ** In Method 1, you use the keywords 'EXECUTE IMMEDIATE'. You ** can only use this method for SQL queries that return no ** results. It cannot reference any C program variables. The ** query is parsed and compliled by the server every time ** the user executes it. ** In this program, you create a table after checking to see ** if it exists, insert a row into it, check the number of ** rows in the table and the drop the table. ** Note that all the statements are non-select. ** ** References : Open Client Embedded SQL/C Programmer's Guide, Reference ** manual - look for the chapter on Dynamic SQL. ** */
/* Forward declarations for error and warning handlers */ void error_handler(); void warning_handler();
int main() { EXEC SQL BEGIN DECLARE SECTION; /* Storage for the login name and password */ CS_CHAR username[30], password[30]; CS_CHAR cmd[100]; EXEC SQL END DECLARE SECTION;
int i=0 ;
EXEC SQL CONNECT :username IDENTIFIED BY :password ; EXEC SQL USE pubs2 ; strcpy(cmd, "if exists (select 1 from sysobjects where name = 'test_tab') drop table test_tab "); EXEC SQL EXECUTE IMMEDIATE :cmd ;
printf("Creating table! \n"); strcpy(cmd, "create table test_tab (col1 int) "); printf("SQL statement being executed : %s\n", cmd); EXEC SQL EXECUTE IMMEDIATE :cmd ; printf("Table created! "); printf("Number of rows in table: %d\n",sqlca.sqlerrd[2]);
printf("\nInserting row into new table .. \n"); strcpy(cmd, " insert test_tab values (100)") ; printf("SQL statement being executed : %s\n", cmd); EXEC SQL EXECUTE IMMEDIATE :cmd ; printf("Row inserted! Number of rows in table : %d\n",sqlca.sqlerrd[2]);
printf("\nDemo complete! Dropping table \n"); strcpy(cmd, " drop table test_tab "); printf("SQL statement being executed : %s\n", cmd); EXEC SQL EXECUTE IMMEDIATE :cmd ;
************************************************************************* dynamic2.cp
/* Program name : dynamic2.cp ** ** Description : This program demonstrates the use of Dynamic SQL Method 2. ** In Method 2, you use 'PREPARE' and 'EXECUTE' to substitute ** data from C variables into a T-SQL statement before sending ** the statement to the server. This statement is 'prepared', ** which means that it is compiled and saved as a temporary ** stored procedure. Each time it is executed, only the ** host variable values are substituted as parameters to the ** stored procedure. ** ** With this method, you can only issue single row selects or ** issue statements that will not retrieve data. ** ** References : Open Client Embedded SQL/C Programmer's Guide, Reference ** manual - see chapter on Dynamic SQL. ** */
int main() { EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_CHAR pub_id[5], pub_name[30], pub_city[20], pub_state[3] ; EXEC SQL END DECLARE SECTION;
char ch[2] ;
EXEC SQL CONNECT :username IDENTIFIED BY :password ; EXEC SQL USE pubs2 ; /* Declare a cursor to retrieve all the key values first */ EXEC SQL DECLARE mycursor CURSOR FOR SELECT pub_id FROM publishers ; EXEC SQL OPEN mycursor ; for (;;) { EXEC SQL FETCH mycursor INTO :pub_id ; if ( sqlca.sqlcode == 100 ) break ; printf("Pub id = %s\n", pub_id); }
/* Prompt the user to choose from the results of the above cursor. Then, ** use dynamic sql to retrieve the record for the given key. The program ** can be run as many times as required, but the following SQL select ** statement will be compiled only once and stored as a temporary stored ** procedure. Each time that we execute the statement, the publisher id ** that we input will be substituted as a dynamic parameter. */ do { fflush (stdin); printf("Please choose from one of the pub ids listed above: "); fflush (stdin); gets(pub_id); EXEC SQL PREPARE sel_stmt FROM "select * from publishers where pub_id = ?"; EXEC SQL EXECUTE sel_stmt INTO :pub_id, :pub_name, :pub_city, :pub_state using :pub_id ;
printf("\n\n Record detail for publisher %s\n", pub_id); printf("\n--------------------------------------\n"); printf(" PUBLISHER ID : %s\n",pub_id); printf(" PUBLISHER NAME : %s\n",pub_name); printf(" PUBLISHER CITY : %s\n",pub_city); printf(" PUBLISHER STATE : %s\n",pub_state); fflush(stdin); strcpy(ch,""); printf(" Continue (Y/N) ? "); gets (ch); strcpy(pub_id,""); strcpy(pub_name,""); strcpy(pub_city,""); strcpy(pub_state,""); } while (toupper(ch[0]) != 'N') ;
************************************************************************* dynamic3.cp
/* Program name : dynamic3.cp ** ** Description : This program demonstrates the use of Dynamic SQL Method 3. ** In Method 3, you use 'PREPARE' statements with cursors to ** return results from a fixed-list SELECT statement that may ** return multiple rows. By fixed-list, we mean that the appl- ** ication must know the number and type of data that will be ** returned and stored in host variables. ** This program uses Method 3 to retrieve a row from a ** cursor and then prompts the user to UPDATE the current row ** using the WHERE CURRENT OF clause. It also shows how the ** current record can be deleted. ** ** References : Open Client Embedded SQL/C Programmer's Guide, Reference ** manual - look for the chapter on Dynamic SQL. ** ** Script file : dynamic3.sql. Note that the table MUST have a unique index. ** */
EXEC SQL BEGIN DECLARE SECTION; /* storage for login name and password */ CS_CHAR username[30], password[30]; CS_CHAR stmt[100], emp_id[6], name[21], grade[6], input_grade[6] ; float salary ; EXEC SQL END DECLARE SECTION;
/* ** Forward declarations of the error and message handlers and ** other subroutines called from main(). */ void error_handler(); void warning_handler(); void print_n_update();
EXEC SQL CONNECT :username IDENTIFIED BY :password ; EXEC SQL USE tempdb ;
strcpy(stmt,"select emp_id, name, grade, salary from employee where grade = ?"); EXEC SQL PREPARE sel_stmt FROM :stmt;
printf("Retrieve records of employees in grade ? [A/B/C]"); fflush(stdin); gets(input_grade); EXEC SQL DECLARE sel_cursor CURSOR FOR sel_stmt ; EXEC SQL OPEN sel_cursor USING :input_grade; for (;;) { EXEC SQL FETCH sel_cursor INTO :emp_id, :name, :grade, :salary ; if ( sqlca.sqlcode == 100 ) { printf("No more rows to fetch. \n"); break ; } print_n_update(); } /* Clean up the opened cursor and prepared statement */ EXEC SQL CLOSE sel_cursor; EXEC SQL DEALLOCATE PREPARE sel_stmt;
/* Commit the changes to the database. This needs to be done as ** in ESQL the default mode is 'chained'. This means that all ** transactions will need to be explicitly commited, else the ** changes made by the application will not be reflected in the ** database. */ EXEC SQL COMMIT WORK ; EXEC SQL DISCONNECT ALL; exit(0); }
/* ** void print_n_update() ** ** This routine displays the current record and gives the user the choice of ** updating the current record with new values through user input. ** Note that the update can easily be changed to a delete operation. ** */ void print_n_update() { char ch[2] ;
printf("\n\n Record detail for employee %s\n", emp_id); printf("\n--------------------------------------\n"); printf(" ID : %s\n",emp_id); printf(" NAME : %s\n",name); printf(" GRADE : %s\n",grade); printf(" SALARY : %f\n",salary); strcpy(ch,""); printf("\n Update this record (Y/N) ? "); gets (ch); if ( toupper(ch[0]) == 'Y' ) { printf("New grade ? "); gets(grade); printf("New salary ? "); scanf("%f",&salary); exec sql update employee set grade = :grade, salary = :salary where current of sel_cursor;
/* NOTE: To delete the current record, simply say: ** EXEC SQL delete employee where CURRENT OF sel_cursor ; */
getchar(); } }
************************************************************************* dynamic3.sql
use tempdb go if exists ( select 1 from sysobjects where name = 'employee' ) drop table employee go create table employee(emp_id char(5), name varchar(20), grade char(5), salary float)
go create unique index myind on employee(emp_id) go insert employee values('1001','Sandy Thomson','A',7000) go insert employee values('1002','Frank Smith','B',4105) go insert employee values('1003','Jill Miller','B',4560) go insert employee values('1004','Keith Piedmont','C',3900) go insert employee values('1005','Phil Cohens','A',9000) go
************************************************************************* dynamic4.cp
/* Program name : dynamic4.cp ** ** Description : This program demonstrates the use of Dynamic SQL Method 4. ** In Method 4, you use 'PREPARE' statements with cursors and ** system descriptors to handle varying-list select statements. ** Use this method when you do not know beforehand the ** number and the datatype of items that the SELECT statement ** will return. ** ** References : Open Client Embedded SQL/C Programmer's Guide, Reference ** manual - look for the chapter on Dynamic SQL. ** */
EXEC SQL BEGIN DECLARE SECTION; /* Storage for login name and record */ CS_CHAR username[30], password[30]; CS_CHAR stmt[150], char_buff[255], colname[20][33]; CS_INT int_buff, descnt, cnt, coltype; CS_FLOAT float_buff; EXEC SQL END DECLARE SECTION;
/* ** Forward declarations of the error and message handlers and ** other subroutines called from main(). */ void error_handler(); void warning_handler(); void get_colnames(); void print_data(); void draw_line();
/* Enter any valid T-SQL SELECT statement */ printf("Please enter a SQL select statement in the form: "); printf("select <column_list> from database.owner.table where <column> = <value> .. \n"); fflush(stdin); gets(stmt); /* Set the maximum number of columns that are to be retrieved */ EXEC SQL ALLOCATE DESCRIPTOR sample_desc WITH max 256; EXEC SQL PREPARE sel_stmt FROM :stmt;
/* EXEC SQL DESCRIBE INPUT sel_stmt using sql descriptor sample_desc; */ /* Now, declare a cursor for the prepared statement. */ EXEC SQL DECLARE sel_cursor CURSOR FOR sel_stmt ;
EXEC SQL OPEN sel_cursor USING SQL DESCRIPTOR sample_desc ; /* Fetch the rows */ EXEC SQL FETCH sel_cursor INTO SQL DESCRIPTOR sample_desc ;
/* get the column names first, because we need them only once. */ get_colnames();
while (sqlca.sqlcode >= 0 ) { print_data(); EXEC SQL FETCH sel_cursor INTO SQL DESCRIPTOR sample_desc ; if (sqlca.sqlcode == 100 ) { printf("End of results. \n"); break ; } printf("\n"); } EXEC SQL CLOSE sel_cursor ; EXEC SQL DEALLOCATE DESCRIPTOR sample_desc ; EXEC SQL DEALLOCATE PREPARE sel_stmt ; EXEC SQL DISCONNECT ALL; exit(0);
/* ** void get_colnames() ** In this function we get the column names in question using the SQL ** descriptor defined in the function above. ** */ void get_colnames() { EXEC SQL GET DESCRIPTOR sample_desc :descnt = count ;
draw_line(); for ( cnt = 1 ; cnt <= descnt ; cnt++ ) { EXEC SQL GET DESCRIPTOR sample_desc VALUE :cnt :colname[cnt] = NAME ; printf("%-25s ", colname[cnt]); } draw_line(); }
/* ** void print_data() ** Routine that uses system descriptors to get the number of columns, the ** type of columns and the data itself. Depending on the type of data being ** returned, we store them in appropriate host variables. */ void print_data() { EXEC SQL GET DESCRIPTOR sample_desc :descnt = count ;
for ( cnt = 1 ; cnt <= descnt ; cnt++ ) { EXEC SQL GET DESCRIPTOR sample_desc value :cnt :coltype = TYPE ; switch (coltype) { case 2: /* NUMERIC type */ case 8: /* FLOAT type */ case 3: /* DECIMAL type */ EXEC SQL GET DESCRIPTOR sample_desc VALUE :cnt :float_buff = DATA ; printf("%15.2f ",float_buff); break ;
case 4 : /* INT data */ case 14 : /* BIT data */ EXEC SQL GET DESCRIPTOR sample_desc VALUE :cnt :int_buff = DATA ; printf("%15d ",int_buff); break ;
case 1 : /* CHAR or VARCHAR type */ case 9 : /* DATETIME type */ case -10 : /* MONEY type */ default : /* Any other type */ EXEC SQL GET DESCRIPTOR sample_desc VALUE :cnt :char_buff = DATA ; printf("%-25s",char_buff); break ;
}; } printf("\n"); }
/* ** void draw_line() ** ** Routine to draw lines before and after the column headings. ** */ void draw_line() { int i;
printf("\n"); for ( i = 0; i< 120; i++) printf("-"); printf("\n"); }
************************************************************************* sybsqlex.h
/* sybsqlex.h - header file for Embedded SQL/C examples */
#define USER "sa" #define PASSWORD ""
#define ERREXIT -1 #define STDEXIT 0
************************************************************************* makefile
# Make the Embedded SQL/C sample programs. # # Change the following definitions as appropriate for your site: MAKE = make CC="$(CC)" AS="$(AS)" LD="$(LD)" AR="$(AR)" CPP="$(CPP)" SYBPLATFORM="$(SYBPLATFORM)" # SHELL = /bin/sh HEADERS =
TARGET1 = indicator TARGET2 = arrays TARGET3 = arrays_cur TARGET4 = short_text TARGET5 = text_image TARGET6 = descriptor TARGET7 = dynamic1 TARGET8 = dynamic2 TARGET9 = dynamic3 TARGET10 = dynamic4 TARGET11 = date_convert TARGET12 = stored_proc
INCLUDE = -I. -I/usr/openwin/include -I$${SYBASE}/include LIBFLAGS = -L$${SYBASE}/lib SYBLIBDIR = $${SYBASE}/lib/ CFLAGS = $(INCLUDE) $(LIBFLAGS) #PRECOMP = $${SYBASE}/bin/cpre -y PRECOMP = /remote/sol_releases/rel1111_conn/bin.org/cpre LINK.c = cc -g $(INCLUDE) $(LIBFLAGS)
#SYBLIBS = -lct -lcs -lcomn -ltcl -lintl SYBLIBS = \ $(SYBLIBDIR)libct.a \ $(SYBLIBDIR)libcs.a \ $(SYBLIBDIR)libcomn.a \ $(SYBLIBDIR)libtcl.a \ $(SYBLIBDIR)libintl.a MATHLIBS = -lm
# platform specific stuff KRC_FLAGS = -C KR_C #SCKLIBS = $(SYBLIBS) -linsck $(MATHLIBS) SCKLIBS = $(SYBLIBS) \ $(SYBLIBDIR)libinsck.a \ $(MATHLIBS) #TLILIBS = $(SYBLIBS) -ltli -lnsl $(MATHLIBS) TLILIBS = $(SYBLIBS) \ $(SYBLIBDIR)libtli.so \ -lnsl \ -ldl \ $(MATHLIBS)
all: $(TARGET1) $(TARGET2) $(TARGET3) $(TARGET4) $(TARGET5) $(TARGET6) \ $(TARGET7) $(TARGET8) $(TARGET9) $(TARGET10) $(TARGET11) $(TARGET12)
$(TARGET1): $(HEADERS) indicator.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c indicator.c $${ESQLIBS}
indicator.c: indicator.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS)" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} indicator.cp
$(TARGET2): $(HEADERS) arrays.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c arrays.c $${ESQLIBS}
arrays.c: arrays.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} arrays.cp
$(TARGET3): $(HEADERS) arrays_cur.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c arrays_cur.c $${ESQLIBS}
arrays_cur.c: arrays_cur.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} arrays_cur.cp
$(TARGET4): $(HEADERS) short_text.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c short_text.c $${ESQLIBS}
short_text.c: short_text.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} short_text.cp
$(TARGET5): $(HEADERS) text_image.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c text_image.c $${ESQLIBS}
text_image.c: text_image.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} text_image.cp
$(TARGET6): $(HEADERS) descriptor.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c descriptor.c $${ESQLIBS}
descriptor.c: descriptor.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} descriptor.cp
$(TARGET7): $(HEADERS) dynamic1.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c dynamic1.c $${ESQLIBS}
dynamic1.c: dynamic1.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} dynamic1.cp
$(TARGET8): $(HEADERS) dynamic2.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c dynamic2.c $${ESQLIBS}
dynamic2.c: dynamic2.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} dynamic2.cp
$(TARGET9): $(HEADERS) dynamic3.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c dynamic3.c $${ESQLIBS}
dynamic3.c: dynamic3.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} dynamic3.cp
$(TARGET10): $(HEADERS) dynamic4.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c dynamic4.c $${ESQLIBS}
dynamic4.c: dynamic4.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} dynamic4.cp
$(TARGET11): $(HEADERS) date_convert.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c date_convert.c $${ESQLIBS}
date_convert.c: date_convert.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} date_convert.cp
$(TARGET12): $(HEADERS) stored_proc.c case $${SYBPLATFORM} in \ axposf|sun4|rs6000|hp800) \ ESQLIBS="$(SCKLIBS)" export ESQLIBS ;; \ ncr|sun_svr4) \ ESQLIBS="$(TLILIBS)" export ESQLIBS ;; \ *) NETLIBS="" ;; \ esac ; \ $(LINK.c) -o $@ $${SYBASE}/include/sybesql.c stored_proc.c $${ESQLIBS}
stored_proc.c: stored_proc.cp case $${SYBPLATFORM} in \ sun4) \ PRECOMPFLAGS="$(KRC_FLAGS) -m" export PRECOMPFLAGS ;; \ rs6000) \ PRECOMPFLAGS="-l -m" export PRECOMPFLAGS ;; \ *) \ PRECOMPFLAGS="-m" export PRECOMPFLAGS ;; \ esac ; \ $(PRECOMP) $${PRECOMPFLAGS} stored_proc.cp