Determining the Value of Built-in I/O Functions
February 28, 2007 Hey, Ted
What follows is a question that I have paraphrased from the emails of various readers of this august publication, who all seem to be encountering a similar issue: “Is it possible to view the value returned by built-in functions, such as %EOF and %FOUND, when working in the green-screen, full-screen debugger?”
The short answer is “No.” The debugger will not show you the result of any function, built-in or user-defined, unless that function is defined to the debugger. (See Undocumented Debugger Function.) The reason for this behavior is that a function is not a variable. A variable is a section of memory, and as such, is easily queried for its current value. A function is executable code that runs when the function is invoked.
However, that does not mean that there is no way to determine the value that an I/O function returns. You just have to go about it another way.
Let’s consider the following trivialized example program snippet.
Fitembl if e k disk D Itnbr s 15a /free chain itnbr itemblmc; if %found(itembl); DoWhatever(); else; DoWhateverElse(); endif;
After the chain operation, %FOUND is either true (*ON) or false (*OFF). The same is true for %ERROR.
Here’s another example:
FMyInfo if e k disk FQSysPrt o f 132 printer /free *inlr = *on; dow '1'; read myinfo; if %eof(myinfo); leave; endif; except pline; enddo; return;
After the read, the %EOF and %ERROR functions are updated with true/false values.
I have heard it said that there’s no need to be able to view the returned values of the functions, since a person can determine how the functions behaved by watching the path of execution. That’s a good point, and that’s what I usually do. But there are times that I would not allow a section of code to execute if I knew what the function had returned, or I would have plugged a value in order to force the program to continue in some other direction. (I assume that those who have asked me this question have similar motives for wanting to know the result of a function call.)
I know of two methods you can use to see a function’s return value. Here’s the more obvious one first.
Method 1: Store the function’s return value in a variable, like this.
FMyInfo if e k disk FQSysPrt o f 132 printer D eof s n /free *inlr = *on; dow '1'; read myinfo; eof = %eof(myinfo); if eof; leave; endif; except pline; enddo; return; /end-free OQSysPrt e pline 1 O name O age 4 +0001
This method is by no means rocket science. Store the result of the %EOF function into variable EOF, then view the value of EOF. Besides being able to view the result of the %EOF function, you can alter the course of program execution by changing the value of the EOF variable before it is tested.
eval eof = '1'
Method 2: Check the status subfield of the file information data structure.
FMyInfo if e k disk infds(MyInfoDS) FQSysPrt o f 132 printer D MyInfoDS ds D MyInfoStatus *status /free *inlr = *on; dow '1'; read myinfo; if %eof(myinfo); leave; endif; except pline; enddo; return; /end-free OQSysPrt e pline 1 O name O age 4 +0001
Add an INFDS keyword to the F spec of the file whose I/O status you want to test, and key the name of a data structure as the keyword’s value. In this case, the data structure is MyInfoDS. Create the data structure and include a status subfield, defined with the literal *STATUS in the “from” entry field of the D spec.
When the program performs an I/O operation to MyInfo, the file information data structure will be updated. If the I/O is successful, the status subfield gets set to all zeros. If a READx operation hits beginning or end of file, the status becomes 11. A failed CHAIN (random read) returns a status code of 11. Status codes of 1000 or above indicate errors. See the iSeries Information Center for more about status codes.
iSeries Information Center, Status Code section