![]() Chapter Contents |
![]() Previous |
![]() Next |
| Examples |
#include <dfhbmsca.h> /* useful BMS definitions */
/* C struct defining Map A, produced by DSECT2C */
#include <sascaga.h>
/* C struct defining Map C, produced by DSECT2C */
#include <sascagc.h>
#include <ctype.h> /* standard C type header */
#include <string.h> /* standard C string handling header */
/* general-purpose variables */
short i;
char rid[6] = "000000"; /* record key, the account number */
char ridb[6] = "000000"; /* record key, for backward paging */
char ridf[6] = "000000"; /* record key, for forward paging */
/* indicates in which direction the browsing */
/* is currently moving: F or B */
char currop;
/* indicates the previous browsing direction */
char lastop;
char status; /* file status: 'H', 'L', or ' ' */
char messages[39]; /* message holding area */
short comlen; /* length of CICS commarea */
char keynum[6]; /* record key, the account number */
/* FILEA record layout */
struct FILEA{
char stat;
char numb[6];
char name[20];
char addrx[20];
char phone[8];
char datex[8];
char amount[8];
char comment[9];
} filea;
/* function prototypes */
void errors(void);
void smnu(void);
void smsg(void);
void not_found(void);
void build_next(void);
void build_prev(void);
void page_forward(void);
void page_backward(void);
void receive(void);
void too_high(void);
void too_low(void);
/* The main function begins here. */
main()
{
/* Prepare to handle paging requests via PF keys. */
EXEC CICS HANDLE AID CLEAR(smsg)
PF1(page_forward)
PF2(page_backward);
/* Prepare to handle error conditions. */
EXEC CICS HANDLE CONDITION ERROR(errors)
MAPFAIL(smsg)
NOTFND(not_found);
/* Read the initial screen. */
EXEC CICS RECEIVE MAP("SASCAGA");
/* Was a starting account number provided? */
if (memcmp(sascaga.keyl,"\0 \0",2) == 0){
/* No, so default to zero. */
strcpy(rid,"000000");
strcpy(ridf,"000000");
}
else{
/* Yes, so validate all of its digits. */
for(i=0;i<=5;i++){
if (isdigit((int) sascaga.KEYI[i]) == 0){
strcpy(messages,"ACCOUNT NUMBER MUST BE NUMERIC");
smnu(); /* There is no return from smnu(). */
}
}
/* Save the starting account number for */
/* use in either direction. */
memcpy(rid,sascaga.keyi,6);
memcpy(ridf,sascaga.keyi,6);
memcpy(ridb,sascaga.keyi,6);
}
/* Initiate the VSAM browse file operation. */
EXEC CICS STARTBR DATASET("FILEA") RIDFLD(rid);
/* Is the current account number 999999 */
/* (the absolute maximum)? */
if (memcmp(rid,"999999",6) != 0){
/* No, so page forward. */
page_forward();
}
else{
/* Yes, so set the status to HIGH and page backward. */
status = 'H';
page_backward();
}
receive(); /* There is no return from receive(). */
} /* end of main function */
/* This function processes a forward paging request. */
void page_forward()
{
currop = 'F'; /* Set the indicator to forward paging mode. */
/* Prepare to handle reading past the end of the file. */
EXEC CICS HANDLE CONDITION ENDFILE(too_high);
memset(&sascagc,'\0',SASCAGCE); /* Clear Map C. */
memcpy(rid,ridf,6);
build_next(); /* Read more records. */
memcpy(ridf,rid,6);
EXEC CICS SEND MAP("SASCAGC") ERASE; /* Display Map C. */
} /* end of page_forward function */
/* This function processes a backward paging request. */
void page_backward()
{
currop = 'B'; /* Set the indicator to backward paging mode. */
/* Prepare to handle reading before the beginning of the file. */
EXEC CICS HANDLE CONDITION ENDFILE(too_low);
memset(&sascagc,',SASCAGCE); /* Clear Map C. */
memcpy(rid,ridb,6);
memcpy(ridf,ridb,6);
/* READPREV commands will reread the last record read by a */
/* READNEXT command, so perform an extra READPREV to account */
/* for this behavior. */
if ((lastop == 'F') && (status != 'H')){
EXEC CICS READPREV DATASET("FILEA") INTO(&filea) RIDFLD(rid)
LENGTH(sizeof(struct FILEA)) KEYLENGTH(sizeof(rid));
}
build_prev(); /* Read more records. */
memcpy(ridb,rid,6);
EXEC CICS SEND MAP("SASCAGC") ERASE; /* Display Map C. */
} /* end of page_backward function */
/* This function controls the continual processing of */
/* page requests. Remember that the user can decide to */
/* press PF1 or PF2 at any time. Pressing these keys */
/* is an implicit request for forward or backward paging, */
/* respectively. When a PF key is pressed, the */
/* appropriate function is driven; then control */
/* returns to the next executable statement within the */
/* for(;;) loop. From that point, normal FORWARD/BACKWARD */
/* <ENTER> key processing continues. */
void receive()
{
/* Continue to process page requests until the CLEAR key is */
/* pressed or the user does not enter a direction indicator. */
for(;;){
/* Remember which direction the reading is going. */
lastop = currop;
/* Read the latest screen. */
EXEC CICS RECEIVE MAP("SASCAGC");
/* When the MAPFAIL condition occurs here, the browse */
/* operation ends, and smsg() will be driven. */
status = ' ';
/* Did the user enter a forward page request by keying an F ? */
if (memcmp(sascagc.diri,"F",1) == 0){
/* Yes, so cause forward paging to occur. */
page_forward();
}
/* Did the user enter a backward page request by keying a B ? */
else
if (memcmp(sascagc.diri,"B",1) == 0){
/* Yes, so cause backward paging to occur. */
page_backward();
}
else{
/* Neither F nor B was keyed, so resend the map. This */
/* eventually results in a MAPFAIL condition and, */
/* therefore, the end of the browse operation. */
EXEC CICS SEND MAP("SASCAGC");
}
} /* end of for(;;) loop */
} /* end of receive() */
/* This function is called when a read is attempted past */
/* the end of file. */
void too_high()
{
/* Set status so that further reads are prevented. */
status = 'H';
memcpy(ridf,rid,6);
memcpy(ridb,rid,6);
/* Indicate that forward paging has ceased. */
sascagc.diro = ' ';
/* Prepare an informative message. */
strcpy(sascagc.msg1o,"Hi-End of File");
sascagc.msg1a= DFHBMASB;
} /* end of too_high() */
/* This function is called when a read is attempted */
/* before the beginning of the file. */
void too_low()
{
/* Set status so that further reads are prevented. */
status = 'L';
strcpy(ridf,"000000");
strcpy(ridb,"000000");
/* Indicate that backward paging has ceased. */
sascagc.diro = ' ';
/* Prepare an informative message. */
strcpy(sascagc.msg2o,"Lo-End of File");
sascagc.msg2a = DFHBMASB;
} /* end of too_low */
/* This function is called when the specified starting */
/* account number is not found. The VSAM browse */
/* operation is ended and appropriate messages are prepared. */
void not_found()
{
strcpy(messages,"End of File - Please Restart");
EXEC CICS ENDBR DATASET("FILEA");
smnu(); /* There is no return from smnu() */
} /* end of not_found() */
/* This function prepares an informative */
/* message and calls smnu(). */
void smsg()
{
strcpy(messages,"Press CLEAR to Exit");
smnu(); /* There is no return from smnu(). */
} /* end of smsg() */
/* This function is called when a severe and */
/* unrecoverable error is detected. It */
/* causes a CICS transaction dump to be taken, */
/* and prepares an error message. */
void errors()
{
EXEC CICS DUMP DUMPCODE("ERRS");
strcpy(messages,"Transaction Terminated");
smnu(); /* There is no return from smnu(). */
} /* end of errors() */
/* This function displays the main menu on */
/* the screen and returns control to CICS. */
void smnu()
{ memset(&sascaga,'\0',SASCAGAE); /* Clear Map A. */
sascaga.msga = DFHBMASB; /* Move the message to the map. */
memcpy(sascaga.msgo,messages,strlen(messages));
memset(messages,'\0',39); /* Clear the message variable. */
EXEC CICS SEND MAP("SASCAGA") ERASE;
EXEC CICS RETURN;
}
/* end of smnu() */
/* This function performs up to four READNEXT */
/* commands to fill the screen in a forward paging mode. */
void build_next()
0
int i;
/* It takes four iterations to fill the screen. */
for(i=1; i<= 4; i++){
EXEC CICS READNEXT DATASET("FILEA") INTO(&filea) RIDFLD(rid)
LENGTH(sizeof(struct FILEA)) KEYLENGTH(sizeof(rid));
/* If you read past the end of the file, STOP. */
if (status == 'H')
break;
switch(i){
case 1:{
/* Move the record fields to line 1 of the map. */
memcpy(sascagc.number1o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name1o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount1o,filea.amount,sizeof(filea.amount));
memcpy(ridb,rid,6);
break;
}
/* end of case: 1 */
case 2:0
/* Move the record fields to line 2 of the map. */
memcpy(sascagc.number2o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name2o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount2o,filea.amount,sizeof(filea.amount));
break;
} /* end of case: 2 */
case 3:0
/* Move the record fields to line 3 of the map. */
memcpy(sascagc.number3o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name3o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount3o,filea.amount,sizeof(filea.amount));
break;
} /* end of case: 3 */
case 4:0
/* Move the record fields to line 4 of the map. */
memcpy(sascagc.number4o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name4o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount4o,filea.amount,sizeof(filea.amount));
break;
} /* end of case: 4 */
} /* end of switch(i) *
} /* end of for loop */ }
} /* end of build_next() */
/* This function performs up to four READPREV commands */
/* to fill the screen in a backward paging mode. */
void build_prev()
0
int i;
/* It takes 4 iterations to fill the screen. */
for(i=1; i <= 4; i++)0
EXEC CICS READPREV DATASET("FILEA") INTO(&filea) RIDFLD(rid)
LENGTH(sizeof(struct FILEA)) KEYLENGTH(sizeof(rid));
/* If we read before the beginning of the file, STOP. */
if (status == 'L')
break;
/* The records will be displayed in ascending order, */
/* so put the last one read at the top of the screen. */
switch(i)0
case 4:0
/* Move the record fields to line 1 of the map. */
memcpy(sascagc.number1o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name1o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount1o,filea.amount,sizeof(filea.amount));
break;
} /* end of case: 4 */
case 3:0
/* Move the record fields to line 2 of the map. */
memcpy(sascagc.number2o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name2o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount2o,filea.amount,sizeof(filea.amount));
break;
} /* end of case: 3 */
case 2:0
/* Move the record fields to line 3 of the map. */
memcpy(sascagc.number3o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name3o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount3o,filea.amount,sizeof(filea.amount));
break;
}
/* end of case: 2 */
case 1:{
/* Move the record fields to line 4 of the map. */
memcpy(sascagc.number4o,filea.numb,sizeof(filea.numb));
memcpy(sascagc.name4o,filea.name,sizeof(filea.name));
memcpy(sascagc.amount4o,filea.amount,sizeof(filea.amount));
break;
} /* end of case: 1 */
} /* end of switch(i) */
} /* end of for loop */
} /* end of build_prev() */
![]() Chapter Contents |
![]() Previous |
![]() Next |
![]() Top of Page |
Copyright © 2001 by SAS Institute Inc., Cary, NC, USA. All rights reserved.