$ ! Copyright © Oracle Corporation 1995. All Rights Reserved. $ ! $ ! SQL$ALL_CDD_RECORD_MOD_C.COM $ ! $ ! This command procedure demonstrates using data dictionary definitions $ ! with SQL module language and a C host language program. This procedure $ ! does the following: $ ! $ ! - Prompts you for the data dictionary path name and creates a $ ! data dictionary directory. $ ! - Defines symbols for SQL and SQLMOD $ ! - Creates the following files: $ ! - SQL$ALL_CDD_RECORD_CREATE_DB.COM -- A command procedure that $ ! creates the database ALL_DATATYPES $ ! - SQL$ALL_CDD_RECORD_CREATE_DEF.COM -- A command procedure that $ ! defines and records in the data dictionary $ ! - SQL$ALL_CDD_RECORD.SQLMOD -- The SQL module $ ! - SQL$ALL_CDD_RECORD_MOD.C -- The host language program $ ! - SQL$ALL_CDD_RECORD_BUILD.COM -- A command procedure that executes $ ! SQL$ALL_CDD_RECORD_CREATE_DB.COM and SQL$ALL_CDD_RECORD_CREATE_DEF.COM, $ ! and compiles, links, and runs the sample application. $ ! - SQL$ALL_CDD_RECORD_DEL_CDD.COM -- A command procedure that deletes $ ! the fields and records in the data dictionary $ ! $ ! - Executes SQL$ALL_CDD_RECORD_CREATE_DB.COM, SQL$ALL_CDD_RECORD_CREATE_DEF.COM, $ ! and SQL$ALL_CDD_RECORD_BUILD.COM $ ! $ write sys$output "Compiling, linking and running sample SQL$ALL_CDD_RECORD demo." $ ! $ ! Prompt for a dictionary pathname and define a logical name for it. $ if P1 .EQS. "" then INQUIRE P1 "Dictionary Path: " $ write sys$output "$DEFINE CDD_SQL_PATH ''p1' -> defined logical for cdd" $ DEFINE CDD_sql_PATH 'p1' $ ! $ sqlmod :== "$sql$mod" $ SQL :== $SQL$ $ ! $ ! Define a directory in the data dictionary. $ DICTIONARY OPERATOR define directo cdd_sql_path. $ ! $ ! Create the command procedure to create the database. $ create SQL$ALL_CDD_RECORD_CREATE_DB.COM ! SQL CREATE DATABASE FILENAME 'ALL_DATATYPES' PATHNAME CDD_SQL_PATH:ALL_DATATYPES; CREATE TABLE ALL_DATATYPES_TABLE ( CHAR_COL CHAR(10), VARCHAR_COL VARCHAR(40), TINYINT_COL TINYINT, SMALLINT_COL SMALLINT, INTEGER_COL INTEGER, REAL_COL REAL, DOUBLE_PREC_COL DOUBLE PRECISION, DATE_COL DATE ); COMMIT; DISCONNECT DEFAULT; $ ! $create SQL$ALL_CDD_RECORD_CREATE_DEF.COM ! This command procedure defines the dictionary definitions. dictionary operator SET DEFAULT CDD_SQL_PATH DEFINE FIELD CHAR_COL datatype text size 10. DEFINE FIELD CHAR_IND DATATYPE SIGNED WORD. DEFINE FIELD VARCHAR_COL DATATYPE VARYING STRING SIZE 40. DEFINE FIELD VARCHAR_IND DATATYPE SIGNED WORD. DEFINE FIELD TINYINT_COL DATATYPE SIGNED BYTE. DEFINE FIELD TINYINT_IND DATATYPE SIGNED WORD. DEFINE FIELD SMALLINT_COL DATATYPE SIGNED WORD. DEFINE FIELD SMALLINT_IND DATATYPE SIGNED WORD. DEFINE FIELD INTEGER_COL DATATYPE SIGNED LONGWORD. DEFINE FIELD INTEGER_IND DATATYPE SIGNED WORD. DEFINE FIELD REAL_COL DATATYPE F_FLOATING. DEFINE FIELD REAL_IND DATATYPE SIGNED WORD. DEFINE FIELD DOUBLE_PREC_COL DATATYPE G_FLOATING. DEFINE FIELD DOUBLE_PREC_IND DATATYPE SIGNED WORD. DEFINE FIELD DATE_COL DATATYPE TEXT SIZE 16. DEFINE FIELD DATE_IND DATATYPE SIGNED WORD. DEFINE RECORD ALL_DATA_REC. CHAR_COL. VARCHAR_COL. TINYINT_COL. SMALLINT_COL. INTEGER_COL. REAL_COL. DOUBLE_PREC_COL. DATE_COL. END RECORD. DEFINE RECORD ALL_DATA_REC_IND. CHAR_IND. VARCHAR_IND. TINYINT_IND. SMALLINT_IND. INTEGER_IND. REAL_IND. DOUBLE_PREC_IND. DATE_IND. END RECORD. DEFINE RECORD ALL_DATA_REC_UPDATE. CHAR_COL. TINYINT_COL. SMALLINT_COL. INTEGER_COL. END RECORD. DEFINE RECORD ALL_DATA_REC_UPDATE_IND. CHAR_IND. TINYINT_IND. SMALLINT_IND. INTEGER_IND. END RECORD. $ create SQL$ALL_CDD_RECORD.SQLMOD -- This SQL module provides the SQL procedures needed by the -- SQL$ALL_CDD_RECORD_MOD.C program. -- -- This program demonstrates the use of data record defintions. -- -- The procedures: insert a row in the table; declare, open, and -- use a cursor to fetch a row; update a row. -- -- This procedure uses the datatypes of data from the common data dictionary -- from the database records. -- -- This procedure also uses the datatypes of record structures inserted -- into the CDD by a command procedure -- -- The program also shows how to use SQL to convert a date to DSRI -- string format. -- -- The GENERAL language allows us to pass VARCHAR data to and from -- the database and the C language program. It also prevents strings -- from being null terminated and the last byte truncated. However the -- calling C program must keep track of the character string length. -------------------------------------------------------------------------- -- Header Information Section -------------------------------------------------------------------------- MODULE SQL_ALL_DATA -- Module name LANGUAGE GENERAL -- Required for CDD and RECORDS AUTHORIZATION SQL_SAMPLE -- Provides default authorization -- identifier PARAMETER COLONS -- Parameters prefixed with colons -------------------------------------------------------------------------- -- DECLARE Statements Section -------------------------------------------------------------------------- DECLARE ALIAS PATHNAME 'CDD_SQL_PATH:ALL_DATATYPES' DECLARE CONVERSIONS CURSOR FOR SELECT * FROM ALL_DATATYPES_TABLE -------------------------------------------------------------------------- -- Procedure Section -------------------------------------------------------------------------- -- This procedure disconnects the database. PROCEDURE DISCONNECT_DATABASE SQLCODE; DISCONNECT DEFAULT; -- This procedure deletes a database (deletes all database files). PROCEDURE DROP_DATABASE SQLCODE; DROP DATABASE PATHNAME 'CDD_SQL_PATH:ALL_DATATYPES'; -- This procedure inserts a row in the table. PROCEDURE STORE_ALL_DATATYPES SQLCODE :ALL_DATA_REC RECORD FROM 'CDD_SQL_PATH:ALL_DATATYPES.RDB$RELATIONS.ALL_DATATYPES_TABLE' END RECORD :ALL_DATA_IND RECORD INDICATOR ARRAY OF 8 SMALLINT END RECORD; INSERT INTO ALL_DATATYPES_TABLE VALUES (:ALL_DATA_REC INDICATOR :ALL_DATA_IND); -- This procedure opens the cursor that has been declared for -- ALL_DATATYPES_TABLE. PROCEDURE OPEN_CURSOR SQLCODE; OPEN CONVERSIONS; -- This procedure closes the cursor that has been declared for -- ALL_DATATYPES_TABLE. PROCEDURE CLOSE_CURSOR SQLCODE; CLOSE CONVERSIONS; -- This procedure fetches all the data from the opened cursor. PROCEDURE FETCH_ALL_DATATYPES SQLCODE :ALL_DATA_REC RECORD FROM 'CDD_SQL_PATH:ALL_DATATYPES.RDB$RELATIONS.ALL_DATATYPES_TABLE' END RECORD :ALL_DATA_IND RECORD INDICATOR ARRAY OF 8 SMALLINT END RECORD; FETCH CONVERSIONS INTO :ALL_DATA_REC INDICATOR :ALL_DATA_IND; -- This procedure fetches all of the data from the opened cursor and -- also converts DATE_COL to a text data type. PROCEDURE FETCH_CONVERT_ALL_DATATYPES SQLCODE :ALL_DATA RECORD FROM 'CDD_SQL_PATH:ALL_DATA_REC' END RECORD :ALL_DATA_IND RECORD INDICATOR ARRAY OF 8 SMALLINT END RECORD; FETCH CONVERSIONS INTO :ALL_DATA INDICATOR :ALL_DATA_IND; -- This procedure updates a row in ALL_DATATYPES_TABLE. PROCEDURE UPDATE_ALL_DATATYPES SQLCODE :ALL_DATA RECORD FROM 'CDD_SQL_PATH:ALL_DATA_REC_UPDATE' END RECORD :ALL_DATA_IND RECORD FROM 'CDD_SQL_PATH:ALL_DATA_REC_UPDATE_IND' END RECORD; UPDATE ALL_DATATYPES_TABLE SET CHAR_COL = :ALL_DATA.CHAR_COL INDICATOR :ALL_DATA_IND.CHAR_IND, TINYINT_COL = :ALL_DATA.TINYINT_COL INDICATOR :ALL_DATA_IND.TINYINT_IND, SMALLINT_COL = :ALL_DATA.SMALLINT_COL INDICATOR :ALL_DATA_IND.SMALLINT_IND, INTEGER_COL = :ALL_DATA.INTEGER_COL INDICATOR :ALL_DATA_IND.INTEGER_IND WHERE CURRENT OF CONVERSIONS; -- This procedure rolls back the transaction. PROCEDURE ROLLBACK_TRANSACTION SQLCODE; ROLLBACK; $ create SQL$ALL_CDD_RECORD_MOD.C /* * This program shows how to use the SQL module language with VAX C and the * data dictionary. It also demonstrates how to pass record structures to * an SQL module program. In the SQL module program, the language is specified * as GENERAL to show how to pass variable length character data, (VARCHAR) * to the SQL module program. * * This program shows how you declare C host language variables * to match a variety of data types and how you can specify those * variables in SQL statements when you store and retrieve column * or null values. The program: * * o Creates the ALL_DATATYPES database and table * o Stores a row using a reference to a host structure and * indicator array occurrences * o Retrieves that row using references to separate fields * and associated indicator variables * o Displays the stored row on the terminal * o Updates some column values in the row * o Displays the changed row on the terminal * o Deletes the database */ /* init is a macro used to initialize a record structure. */ #define init(n){int i;char *j;j = &n; for(i=0;i #include struct date_str { char year_col1[2]; char year_col2[2]; char month_col[2]; char day_col[2]; char hour_col[2]; char minute_col[2]; char second_col[2]; char hundredth_col[2]; } *date_ptr; /*Declare all SQL module language calls */ extern long int drop_database(); extern long int disconnect_database(); extern long int store_all_datatypes(); extern long int open_cursor(); extern long int close_cursor(); extern long int fetch_all_datatypes(); extern long int fetch_convert_all_datatypes(); extern long int update_all_datatypes(); extern long int rollback_transaction(); main() { /* * Declare the variable for monitoring execution status of SQL * statements. */ int SQLCODE; /* Declare a structure for row-level operations. The structure * has subordinate elementary variables for most column-level * operations. */ /* Text descriptor declaration. */ struct dsc$descriptor_s t_dsc; /* String variable for use with SYS$BINTIM and SYS$ASCTIM routines. */ char vms_string_date[24]; /* Declare string variables for use when you want SQL to perform * conversions between DATE and char data types. In this case, * the DSRI rather than the VMS format is required. Note that only * nine characters are needed if you do not plan to store or retrieve * the time segment. */ char dup_year_col2[3]; char dup_month_col[3]; char dup_day_col[3]; char dup_hour_col[3]; char dup_minute_col[3]; /* Use indicator array for handling null values when an SQL statement * performs operations at the record or row level. */ short int indicator_item[8] = {0,0,0,0,0,0,0,0}; /* Use indicator variables for handling null values when an SQL * statement performs operations at the field or column level. */ #dictionary "CDD_SQL_PATH:ALL_DATATYPES.RDB$RELATIONS.ALL_DATATYPES_TABLE" struct all_datatypes_table all_datatypes_record; #dictionary "CDD_SQL_PATH:ALL_DATA_REC_IND" struct all_data_rec_ind all_datatypes_record_ind; #dictionary "CDD_SQL_PATH:ALL_DATA_REC" struct all_data_rec all_datatypes_record_1; #dictionary "CDD_SQL_PATH:ALL_DATA_REC_UPDATE" struct all_data_rec_update all_datatypes_update; #dictionary "CDD_SQL_PATH:ALL_DATA_REC_UPDATE_IND" struct all_data_rec_update_ind all_datatypes_update_ind; /* Create a pointer that maps to varchar structure in record */ varchar(sizeof (all_datatypes_record.varchar_col)-2) *varchar_ptr; /* Use a variable for size of character string */ int char_col_size; char_col_size = sizeof(all_datatypes_record.char_col); /* Move values to main variables. Usually, a program * would first initialize all main variables and indicator * variables before accepting each set of main variable * values from a terminal or data file. To keep this program * short, simply store a set of literals and rely on an * initialization of 0 for indicator variables. (A value of 0 in * an indicator variable ensures that a value in an associated * main variable is stored.) */ init(all_datatypes_record); init(all_datatypes_record_1); init(all_datatypes_record_ind); init(all_datatypes_update); init(all_datatypes_update_ind); strncpy (all_datatypes_record.char_col, "SAM O'DELL",char_col_size); all_datatypes_record.tinyint_col = -128; all_datatypes_record.smallint_col = -32768; /*all_datatypes_record.integer_col = -2147483648;*/ all_datatypes_record.integer_col = 0X80000000; all_datatypes_record.real_col = 0.1234567; all_datatypes_record.double_prec_col = 0.123456789012345; t_dsc.dsc$b_class = DSC$K_CLASS_S; t_dsc.dsc$b_dtype = DSC$K_DTYPE_T; t_dsc.dsc$w_length = 23; t_dsc.dsc$a_pointer = "22-APR-1987 10:17:56.00"; SYS$BINTIM (&t_dsc, &all_datatypes_record.date_col ); /* Use varchar pointer into all_datatypes_record */ varchar_ptr = &all_datatypes_record.varchar_col; strcpy (varchar_ptr->data, "This string is 38 characters in length"); varchar_ptr -> length = strlen(varchar_ptr -> data); /* The following "if" statements evaluate contents of main variables * and then set indicator variables as appropriate. The * conditional evaluation is unnecessary in this particular program, * but is appropriate for programs that store multiple rows and * permit null values for columns associated with main variables. */ if (strcmp (all_datatypes_record.char_col, " " ) == 0) indicator_item[0] = -1; if (strcmp( varchar_ptr -> data, " " ) == 0 ) indicator_item[1] = -1; if (all_datatypes_record.tinyint_col == 0) indicator_item[2] = -1; if (all_datatypes_record.smallint_col == 0) indicator_item[3] = -1; if (all_datatypes_record.integer_col == 0) indicator_item[4] = -1; if (all_datatypes_record.real_col == 0) indicator_item[5] = -1; if (all_datatypes_record.double_prec_col == 0) indicator_item[6] = -1; if ( *(double *)&all_datatypes_record.date_col == 0) indicator_item[7] = -1; /* The following INSERT statement transfers an entire structure * as a row. Because the INSERT statement does not list columns * in ALL_DATATYPES_TABLE in the order that they correspond to * elementary fields in ALL_DATATYPES_RECORD, the statement * assumes that the current number and order of columns in the * table correspond correctly to number and order of fields * in the structure. This is appropriate when a table definition * is stable (as is true here because the program creates the * table). */ printf ("\n\n Storing 1 record in database"); store_all_datatypes(&SQLCODE,&all_datatypes_record,&indicator_item); if (SQLCODE < 0 ) goto sql_error_1 ; /* Initialize record */ varchar_ptr = 0; init(all_datatypes_record); init(all_datatypes_record_ind); /* Now retrieve and display the row. */ printf ("\n\n Opening cursor and fetching record"); open_cursor(&SQLCODE); if (SQLCODE < 0 ) goto sql_error_1 ; fetch_all_datatypes(&SQLCODE,&all_datatypes_record,&all_datatypes_record_ind); if (SQLCODE < 0 ) goto sql_error_1 ; /* Display the stored row. */ printf ("\nThis is the stored row."); if (all_datatypes_record_ind.char_ind < 0) printf ("\n\nCHAR_COL: NULL"); else printf ("\nCHAR_COL: %*.*s",char_col_size, char_col_size, all_datatypes_record.char_col); if (all_datatypes_record_ind.varchar_ind < 0) printf ("\nVARCHAR_COL: NULL"); else varchar_ptr = &all_datatypes_record.varchar_col; printf ("\nVARCHAR_COL: %*.*s", varchar_ptr -> length, varchar_ptr -> length, varchar_ptr -> data ); if (all_datatypes_record_ind.tinyint_ind < 0) printf ("\nTINYINT_COL: NULL"); else printf ("\nTINYINT_COL: %d", all_datatypes_record.tinyint_col); if (all_datatypes_record_ind.smallint_ind < 0) printf ("\nSMALLINT_COL: NULL"); else printf ("\nSMALLINT_COL: %d", all_datatypes_record.smallint_col); if (all_datatypes_record_ind.integer_ind < 0) printf ("\nINTEGER_COL: NULL"); else printf ("\nINTEGER_COL: %d", all_datatypes_record.integer_col); if (all_datatypes_record_ind.real_ind < 0) printf ("\nREAL_COL: NULL"); else printf ("\nREAL_COL: %12.7f", all_datatypes_record.real_col); if (all_datatypes_record_ind.double_prec_ind < 0) printf ("\ndouble_prec_COL: NULL"); else printf ("\ndouble_prec_COL: %21.14e", all_datatypes_record.double_prec_col); if (all_datatypes_record_ind.date_ind < 0) printf ("\nDATE_COL: NULL"); else { t_dsc.dsc$b_class = DSC$K_CLASS_S; t_dsc.dsc$b_dtype = DSC$K_DTYPE_T; t_dsc.dsc$w_length = 23; t_dsc.dsc$a_pointer = &vms_string_date; SYS$ASCTIM( 0, &t_dsc, &all_datatypes_record.date_col, 0 ); vms_string_date[23] = 0; printf ("\nDATE_COL: %s", vms_string_date); } /* Modify some columns in the fetched row. Modify all unscaled * fixed-point binary columns to have null values. Change the name * in CHAR_col to be mixed case. * * Set indicator variables to which you plan to refer in * an UPDATE statement. Normally, these assignment statements * would be subordinate to conditional statements that evaluate * main variable values. */ all_datatypes_update_ind.char_ind = 0; all_datatypes_update_ind.smallint_ind = -1; all_datatypes_update_ind.integer_ind = -1; /* Change the old value in char_col and tinyint_col. */ strncpy (all_datatypes_update.char_col, "Sam O'Dell", char_col_size); all_datatypes_update.tinyint_col = 127; /* Update the row. */ printf ("\n\n Updating current row"); update_all_datatypes( &SQLCODE, &all_datatypes_update, &all_datatypes_update_ind); if (SQLCODE < 0 ) goto sql_error_1 ; /* Close and then open the cursor again to reposition the cursor on * the first row and display the changed row. This time, retrieve * DATE_COL by fetching its value and placing it into string_date_col * rather than bin_date_col. */ printf ("\n\n Closing cursor"); close_cursor(&SQLCODE); if (SQLCODE < 0 ) goto sql_error_1 ; /* initialize data */ init(all_datatypes_record_ind); varchar_ptr = 0; printf ("\n\n Fetching updated row with date conversion"); open_cursor(&SQLCODE); if (SQLCODE < 0 ) goto sql_error_1 ; fetch_convert_all_datatypes(&SQLCODE,&all_datatypes_record_1, &all_datatypes_record_ind); if (SQLCODE < 0 ) goto sql_error_1 ; /* Display the changed row. */ printf ("\n\nThis is the changed row."); if (all_datatypes_record_ind.char_ind < 0) printf ("\n\nCHAR_COL: NULL"); else printf ("\nCHAR_COL: %*.*s", char_col_size, char_col_size, all_datatypes_record_1.char_col); if (all_datatypes_record_ind.varchar_ind < 0) printf ("\nVARCHAR_COL: NULL"); else varchar_ptr = &all_datatypes_record_1.varchar_col; printf ("\nVARCHAR_COL: %*.*s",varchar_ptr -> length, varchar_ptr -> length, varchar_ptr -> data ); if (all_datatypes_record_ind.tinyint_ind < 0) printf ("\nTINYINT_COL: NULL"); else printf ("\nTINYINT_COL: %d", all_datatypes_record_1.tinyint_col); if (all_datatypes_record_ind.smallint_ind < 0) printf ("\nSMALLINT_COL: NULL"); else printf ("\nSMALLINT_COL: %d", all_datatypes_record_1.smallint_col); if (all_datatypes_record_ind.integer_ind < 0) printf ("\nINTEGER_COL: NULL"); else printf ("\nINTEGER_COL: %d", all_datatypes_record_1.integer_col); if (all_datatypes_record_ind.real_ind < 0 ) printf ("\nREAL_COL: NULL"); else printf ("\nREAL_COL: %12.7f", all_datatypes_record_1.real_col); if (all_datatypes_record_ind.double_prec_ind < 0) printf ("\ndouble_prec_COL: NULL"); else printf ("\ndouble_prec_COL: %21.14e", all_datatypes_record_1.double_prec_col); if (all_datatypes_record_ind.date_ind < 0) printf ("\nDATE_COL: NULL"); else { date_ptr = &all_datatypes_record_1.date_col; strncpy(dup_year_col2,date_ptr -> year_col2,2); dup_year_col2[2] = 0; strncpy(dup_month_col, date_ptr -> month_col,2); dup_month_col[2] = 0; strncpy(dup_day_col, date_ptr -> day_col,2); dup_day_col[2] = 0; strncpy(dup_hour_col, date_ptr -> hour_col,2); dup_hour_col[2] = 0; strncpy(dup_minute_col, date_ptr -> minute_col,2); dup_minute_col[2] = 0; printf ("\nDATE_COL: %s/%s/%s %s:%s", dup_month_col, dup_day_col, dup_year_col2, dup_hour_col, dup_minute_col); } /* End the transaction so the database can be deleted. First change * error handling so that actions are appropriate for failure of * the ROLLBACK, DISCONNECT, or DROP DATABASE statement. */ printf ("\n\n Rolling back transaction"); rollback_transaction(&SQLCODE); if (SQLCODE < 0 ) goto sql_error_2 ; printf ("\n\n Disconnected from database."); disconnect_database(&SQLCODE); if (SQLCODE < 0 ) goto sql_error_2 ; /* Delete the database and stop the program with normal exit status. */ printf ("\n\n Deleting database by pathname."); drop_database(&SQLCODE); if (SQLCODE < 0 ) goto sql_error_2 ; SYS$EXIT(1); /* Error-handling sections */ sql_error_1: printf ("\nSQLCODE is %d", SQLCODE); printf ("\nError on attempt to create table, or on"); printf ("\nattempt to insert, update, or retrieve data."); rollback_transaction(SQLCODE); if (SQLCODE < 0) { printf ("\nROLLBACK failed. Delete database files manually."); SQL$SIGNAL(); } sql_error_2: printf ("\nSQLCODE is %d", SQLCODE); printf ("\nDatabase could not be deleted."); printf ("\nDelete database files manually."); SQL$SIGNAL(); } $ create SQL$ALL_CDD_RECORD_DEL_CDD.COM DICTIONARY OPERATOR set default CDD_SQL_PATH delete record *. delete field *. $ create SQL$ALL_CDD_RECORD_BUILD.COM $ deck $ ! $! Create the database. $@SQL$ALL_CDD_RECORD_CREATE_DB.COM $ ! $! Create the dictionary definitions. $@SQL$ALL_CDD_RECORD_CREATE_DEF.COM $ ! $! Compile the SQL module. $ sqlmod SQL$ALL_CDD_RECORD/ansi_parameters $ ! $ ! Compile the C program. $ ! $ ! Although C does not have data types for DATE or VARCHAR, the C compiler $ ! does allocate the appropriate space when it includes the record from the $ ! dictionary. Ignore informational messages from the compiler about $ ! unsupported data types. $ ! Use the /NOG_FLOAT qualifier for D_FLOAT representation of DOUBLE PRECISION $ ! $write sys$output "Please ignore informational messages. They are expected." $cc/g_float SQL$ALL_CDD_RECORD_MOD/list/nodebug/noopt $ ! $ ! Link the application. $link/nodebug SQL$ALL_CDD_RECORD_MOd, SQL$ALL_CDD_RECORD,sys$input/opt sql$user/lib sys$library:vaxcrtlg/share $write sys$output " Compiling and linking the sample application." $write sys$output "Running the sample application" $ run SQL$ALL_CDD_RECORD_MOD $write sys$output "@SQL$ALL_CDD_RECORD_DEL_CDD after running application" $exit $eod $write sys$output "Running SQL$ALL_CDD_RECORD_BUILD to build database, load data dictionary," $ @SQL$ALL_CDD_RECORD_BUILD.COM