ibm-information-center/dist/eclipse/plugins/i5OS.ic.apis_5.4.0.1/qprstree.htm

1935 lines
60 KiB
HTML
Raw Permalink Normal View History

2024-04-02 14:02:31 +00:00
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8">
<meta name="Copyright" content="Copyright (c) 2006 by IBM Corporation">
<title>Qp0lProcessSubtree()--Process a Path Name</title>
<!-- Begin Header Records ========================================== -->
<!-- All rights reserved. Licensed Materials Property of IBM -->
<!-- US Government Users Restricted Rights -->
<!-- Use, duplication or disclosure restricted by -->
<!-- GSA ADP Schedule Contract with IBM Corp. -->
<!-- Unix2 SCRIPT J converted by B2H R4.1 (346) (CMS) by V2KEA304 -->
<!-- at RCHVMW2 on 17 Feb 1999 at 11:05:09 -->
<!-- Change History: -->
<!-- 010807 JTROUS,ROSCKES - IASP changes, D98416, v5r2 -->
<!-- 011022 JTROUS Changes from API Review 1, V5R2 -->
<!-- 010514 JTROUS Changes to authority doc, v5r3 -->
<!-- 020618 EMIG: updated for NFS threadsafety, V5R3 -->
<!-- 0206?? JET: This file has undergone html cleanup -->
<!-- 020718 MFENLON: updated for QFileSvr.400 threadsafety, V5R3 -->
<!-- 021021 VONBERGE: Add new qsys.lib usrprf auth reqs. D99381.1 -->
<!-- 040315 JTROUS: Fix compile problem in example, V5R4, no chg flg-->
<!-- 040721 JTROUS: fix OS/400 reference, no change flag, V5R4 -->
<!-- 050406 JTROUS: fix enums, no change flag, V5R4 -->
<!-- 050518 RTHEIS: Update object locking usage notes, -->
<!-- D93319, V5R4. -->
<!--End Header Records -->
<link rel="stylesheet" type="text/css" href="../rzahg/ic.css">
</head>
<body>
<a name="Top_Of_Page"></a>
<!-- Java sync-link -->
<script type="text/javascript" language="Javascript" src="../rzahg/synch.js">
</script>
<h2>Qp0lProcessSubtree()--Process a Path Name</h2>
<div class="box" style="width: 70%;">
<!-- iddvc RMBR -->
<br>
&nbsp;&nbsp;Syntax<br>
<pre>
#include &lt;Qp0lstdi.h&gt;
int Qp0lProcessSubtree (
Qlg_Path_Name_T *<em>Path_Name</em>,
uint <em>Subtree_level</em>,
Qp0l_Objtypes_List_t *<em>Objtypes_array_ptr</em>,
uint <em>Local_remote_obj</em>,
Qp0l_IN_EXclusion_List_t *<em>IN_EXclusion_ptr</em>,
uint <em>Err_recovery_action</em>,
Qp0l_User_Function_t *<em>UserFunction_ptr</em>,
void *<em>Function_CtlBlk_ptr, ...</em>);
</pre>
<br>
&nbsp;&nbsp;Service Program Name: QP0LLIB2<br>
<!-- iddvc RMBR -->
<br>
&nbsp;&nbsp;Default Public Authority: *USE<br>
<!-- iddvc RMBR -->
<br>
&nbsp;&nbsp;Threadsafe: Conditional; see <a href="#USAGE">Usage Notes</a>.<br>
<!-- iddvc RMBR -->
<br>
</div>
<p>The <strong>Qp0lProcessSubtree()</strong> function searches the directory
tree under a specific path name. It selects and passes objects, one at a time,
to an exit program that is identified on its call. The exit program can be
either a procedure or a program.</p>
<p><strong>Qp0lProcessSubtree()</strong> performs recursive read operations to
access any object in any file system. The order in which objects are selected
and passed to the exit program can vary within a given file system and within a
given directory, dependent on file system rules. The only guaranteed ordering
is that all selected objects within a given directory are passed to the exit
program before the parent directory is passed to the exit program.</p>
<br>
<h3>Parameters</h3>
<dl>
<dt><strong><em>Path_Name</em></strong></dt>
<dd>(Input) The path name where <strong>Qp0lProcessSubtree()</strong> starts
its search. All relative path names are relative to the current directory at
the time of the call to <strong>Qp0lProcessSubtree()</strong>. This path name
is in the Qlg_Path_Name_T format. For more information on this structure, see
<a href="../apiref/pns.htm">Path Name Format</a>. The <em>Path_Name</em> parameter must
be NULL to use the <em>IN_EXclusion_ptr</em> parameter to enter multiple path
names for inclusion on a single call to <strong>
Qp0lProcessSubtree()</strong>.<br>
<br>
</dd>
<dt><strong><em>Subtree_level</em></strong></dt>
<dd>(Input) An unsigned integer that tells <strong>
Qp0lProcessSubtree()</strong> whether or not to open subdirectories in the path
being processed. Valid values follow:
<dl compact>
<dt><em><strong>0</strong></em></dt>
<dd><strong>QP0L_SUBTREE_YES:</strong> All subdirectories are opened by
<strong>Qp0lProcessSubtree()</strong> so that the objects they contain are sent
to the exit program if they meet the caller's selection criteria.</dd>
<dt><em><strong>1</strong></em></dt>
<dd><strong>QP0L_SUBTREE_NO:</strong> Only first-level objects are processed.
The names of subdirectories, which meet the selection criteria, are passed to
the exit program, but they are not opened by <strong>
Qp0lProcessSubtree()</strong>. Thus, the objects the subdirectories contain are
not matched against selection criteria and therefore are not sent to the exit
program.</dd>
</dl>
<br>
<br>
</dd>
<dt><strong><em>Objtypes_array_ptr</em></strong></dt>
<dd>(Input) A pointer to an array of object types. Each entry in the array
identifies an object type that <strong>Qp0lProcessSubtree()</strong> uses to
determine what will be passed to the exit program. The Number of object types
field contains the total number of object types in the array. A NULL pointer
means that there is no filtering according to object type and that all object
types that meet other selection criteria are passed to the exit program.
<p>The structure for this parameter follows.</p>
<p><a name="Table_1-43"><strong>Object Types Array Pointer</strong></a></p>
<table border width="80%">
<!-- cols="10 10 20 60" -->
<tr>
<th align="center" valign="bottom" colspan="2">Offset</th>
<th align="left" valign="bottom" rowspan="2">Type</th>
<th align="left" valign="bottom" rowspan="2">Field</th>
</tr>
<tr>
<th align="center" valign="bottom">Dec</th>
<th align="center" valign="bottom">Hex</th>
</tr>
<tr>
<td align="center" valign="top" width="10%">0</td>
<td align="center" valign="top" width="10%">0</td>
<td align="left" valign="top" width="20%">BINARY(4)</td>
<td align="left" valign="top" width="60%">Number of object types</td>
</tr>
<tr>
<td align="center" valign="top">4</td>
<td align="center" valign="top">4</td>
<td align="left" valign="top">ARRAY(*) of CHAR(11)</td>
<td align="left" valign="top">Array of object types structure</td>
</tr>
</table>
<br>
<br>
<dl compact>
<dt><em><strong>Array of object types structure</strong></em></dt>
<dd>An array identifying each object type used to determine what will be passed
to the exit program when processing a path. Each entry is limited to 11
characters, including a NULL terminator, and is padded with blanks. Object
types must be entered in standard object type format which is all
capital letters, preceded by an asterisk (*). For a complete list of the
available object types, see <a href="../rbam6/rbam6objecttypes.htm">Object
Types</a> in the CL topic.<br>
<p><strong>Qp0lProcessSubtree()</strong> verifies that valid object
types are entered and returns the <em>errno</em> EINVAL when an object type
that is not valid is entered. Although some object types are scoped to a
specific file system, <strong>Qp0lProcessSubtree()</strong> does not validate
object types according to file systems.</p>
<p>Valid special values for this parameter follow:</p>
<table cellpadding="5">
<!-- cols="15 85" -->
<tr>
<td align="left" valign="top"><em><strong>*ALLDIR:</strong></em></td>
<td align="left" valign="top">Select all directory object types. This includes
*LIB, *DIR, *FLR, *FILE, and *DDIR object types.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>*ALLQSYS:</strong></em></td>
<td align="left" valign="top">Select all QSYS.LIB object types. This includes
all objects in the QSYS.LIB file system and all independent ASP QSYS.LIB file
systems which are available when the API is first called.
<p><strong>Note</strong>: <em>IN_EXclusion_ptr</em> must also be specified as
an inclusion array. If *NOQSYS is specified, *ALLQSYS cannot also be
specified.</p>
</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>*ALLSTMF:</strong></em></td>
<td align="left" valign="top">Select all stream file object types. This
includes *MBR, *DOC, *STMF, *DSTMF, and *USRSPC object types.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>*MBR:</strong></em></td>
<td align="left" valign="top">Select all database file member
types.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>*NOQSYS:</strong></em></td>
<td align="left" valign="top">Exclude all QSYS.LIB object types. This includes
all objects in the QSYS.LIB file system and all independent ASP QSYS.LIB file
systems which are available when the API is first called.
<p><strong>Note</strong>: This special value only has meaning if '/' or
'/asp_name' is specified for the <em>Path_Name</em> parameter (where
asp_name is the name of an independent ASP which is available when the API is
first called). Additionally, if <em>IN_EXclusion_ptr</em> is specified, it must
only be as an exclusion array. If *ALLQSYS is specified, *NOQSYS cannot also be
specified.</p>
</td>
</tr>
</table>
</dd>
<dt><em><strong>Number of object types</strong></em></dt>
<dd>The number of types included in the search.</dd>
</dl>
<br>
<br>
</dd>
<dt><strong><em>Local_remote_obj</em></strong></dt>
<dd>(Input) An unsigned integer that tells <strong>
Qp0lProcessSubtree()</strong> whether to select only local objects, only remote
objects, or both. Note that the decision of whether a file is local or remote
varies according to the respective file system rules. Objects in file systems
that do not carry either a local or remote indicator are treated as remote.
Valid values follow:
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em><strong>0</strong></em></td>
<td align="left" valign="top"><strong>QP0L_LOCAL_REMOTE_OBJ:</strong> Both
local and remote objects are passed to the exit program.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>1</strong></em></td>
<td align="left" valign="top"><strong>QP0L_LOCAL_OBJ:</strong> Only local
objects are passed to the exit program.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>2</strong></em></td>
<td align="left" valign="top"><strong>QP0L_REMOTE_OBJ:</strong> Only remote
objects are passed to the exit program.</td>
</tr>
</table>
<br>
<br>
</dd>
<dt><strong><em>IN_EXclusion_ptr</em></strong></dt>
<dd>(Input) A pointer to an array of pointers. Each pointer in the array points
to a specific path name that identifies a directory, and all of its
subdirectories, that <strong>Qp0lProcessSubtree()</strong> either includes or
excludes in its search to find objects that meet the caller's input criteria.
If this pointer is not NULL, the IN_EXclusion pointer type must indicate
whether the list is an inclusive or exclusive list. The Number of pointers
field must contain the number of path names for inclusion or exclusion on the
search.
<p>Use an inclusive list to specify multiple path names for searches on a
single call to <strong>Qp0lProcessSubtree()</strong> versus using the <em>
Path_Name</em> parameter, which searches only one path per call. The <em>
Path_Name</em> parameter and an inclusive list are mutually exclusive. EINVAL
is returned if both parameters are specified. The <em>IN_EXclusion_ptr</em>
must be NULL if not used. All of the rules that apply to a single <em>
Path_Name</em> entry apply to each inclusive list entry.</p>
<p>While an inclusion list allows the caller of <strong>
Qp0lProcessSubtree()</strong> to identify multiple path names for processing,
<strong>Qp0lProcessSubtree()</strong> does not perform any verification to
ensure uniqueness of path names or to verify any other relationship between
path names entered in the inclusion array. For example, if the path names
entered represent nested directories, <strong>Qp0lProcessSubtree()</strong>
calls the exit program multiple times without any error message or other
notification of this nesting.</p>
<p>Specify the root directory for a given file system as an exclusive list
entry to eliminate that file system from a search.</p>
<p>All relative path names are relative to the current directory of the job
that calls <strong>Qp0lProcessSubtree()</strong>.</p>
<p>The structure for this parameter follows.</p>
<p><a name="Table_1-44"><strong>IN_EXclusion Pointer</strong></a></p>
<p>This points to a list of path names to either include or exclude from a
search.</p>
<table border width="80%">
<!-- cols="10 10 20 60" -->
<tr>
<th align="center" valign="bottom" colspan="2">Offset</th>
<th align="left" valign="bottom" rowspan="2">Type</th>
<th align="left" valign="bottom" rowspan="2">Field</th>
</tr>
<tr>
<th align="center" valign="bottom">Dec</th>
<th align="center" valign="bottom">Hex</th>
</tr>
<tr>
<td align="center" valign="top" width="10%">0</td>
<td align="center" valign="top" width="10%">0</td>
<td align="left" valign="top" width="20%">BINARY(4)</td>
<td align="left" valign="top" width="60%">IN_EXclusion pointer type</td>
</tr>
<tr>
<td align="center" valign="top">4</td>
<td align="center" valign="top">4</td>
<td align="left" valign="top">BINARY(4)</td>
<td align="left" valign="top">Number of pointers</td>
</tr>
<tr>
<td align="center" valign="top">8</td>
<td align="center" valign="top">8</td>
<td align="left" valign="top">CHAR(8)</td>
<td align="left" valign="top">Reserved</td>
</tr>
<tr>
<td align="center" valign="top">16</td>
<td align="center" valign="top">10</td>
<td align="left" valign="top">ARRAY(*)</td>
<td align="left" valign="top">Path name pointers</td>
</tr>
</table>
<br>
<br>
<dl compact>
<dt><em><strong>IN_EXclusion pointer type</strong></em></dt>
<dd>Whether a path name array contains directories that are included or
contains directories that are excluded. Valid values follow:
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em><strong>0</strong></em></td>
<td align="left" valign="top"><strong>QP0L_INCLUSION_TYPE:</strong> An
inclusion array is identified.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>1</strong></em></td>
<td align="left" valign="top"><strong>QP0L_EXCLUSION_TYPE:</strong> An
exclusion array is identified.</td>
</tr>
</table>
</dd>
<dt><em><strong>Number of pointers</strong></em></dt>
<dd>The number of path name pointers that are in the inclusion or exclusion
array.</dd>
<dt><em><strong>Path name pointers</strong></em></dt>
<dd>An array of pointers. Each pointer points to a path name that is included
or excluded. Each path name must follow the Qlg_Path_Name_T structure. For more
information on this structure, see <a href="../apiref/pns.htm">Path Name Format</a>.</dd>
<dt><em><strong>Reserved</strong></em></dt>
<dd>A reserved field. This field must be set to binary zero.</dd>
</dl>
<br>
<br>
</dd>
<dt><strong><em>Err_recovery_action</em></strong></dt>
<dd>(Input) An unsigned integer that describes how <strong>
Qp0lProcessSubtree()</strong> handles errors that are not severe enough to
force the API to end processing. Valid values follow:
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em><strong>0</strong></em></td>
<td align="left" valign="top"><strong>QP0L_PASS_WITH_ERRORID:</strong> Calls
the exit program and specifies the name (when the name is available) of the
object being accessed when an error occurs. This value also sends a valid <em>
errno</em> to the exit program.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>1</strong></em></td>
<td align="left" valign="top"><strong>QP0L_BYPASS_NO_ERRORID:</strong> Bypasses
the object being accessed when an error occurs, and moves to process the next
object in the tree without notification to the calling program or to the exit
program that an error has occurred.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>2</strong></em></td>
<td align="left" valign="top"><strong>QP0L_JOBLOG_NO_ERRORID:</strong> Sends
message CPDA1C0 to the job log to identify the object being accessed when an
error occurs. This value returns to process the next object without
notification to the calling program or to the exit program that an error has
occurred.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>3</strong></em></td>
<td align="left" valign="top"><strong>QP0L_NULLNAME_ERRORID:</strong> Calls the
exit program with a NULL object name and a valid <em>errno</em>.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>4</strong></em></td>
<td align="left" valign="top"><strong>QP0L_END_PROCESS_SUBTREE:</strong> Quits
<strong>Qp0lProcessSubtree()</strong> when an error occurs, and returns to the
calling program, regardless of the error type. Note that the exit program is
still given a call but cannot override the caller's decision to end
processing. Calling the exit program allows the exit program to perform other
tasks before the API returns to the caller. For example, the exit program can
put information in the function control block that can be processed by the
caller when the caller regains control.</td>
</tr>
</table>
<br>
<br>
</dd>
<dt><strong><em>UserFunction_ptr</em></strong></dt>
<dd>(Input) A pointer to the name of an exit program that the caller wants
<strong>Qp0lProcessSubtree()</strong> to call upon finding an object that
matches the selection criteria. This exit program can be either a procedure or
a program. See <a href="xprstree.htm">Process a Path Name Exit Program</a> for
the syntax of the user exit program.
<p>The structure for this parameter follows.<br>
</p>
<p><a name="Table_1-45"><strong>User Function Pointer</strong></a></p>
<p>This points to the user exit program. The exit program can be a procedure or
a program.</p>
<table border width="80%">
<!-- cols="10 10 20 60" -->
<tr>
<th align="center" valign="bottom" colspan="2">Offset</th>
<th align="left" valign="bottom" rowspan="2">Type</th>
<th align="left" valign="bottom" rowspan="2">Field</th>
</tr>
<tr>
<th align="center" valign="bottom">Dec</th>
<th align="center" valign="bottom">Hex</th>
</tr>
<tr>
<td align="center" valign="top" width="10%">0</td>
<td align="center" valign="top" width="10%">0</td>
<td align="left" valign="top" width="20%">BINARY(4)</td>
<td align="left" valign="top" width="60%">Function type flag</td>
</tr>
<tr>
<td align="center" valign="top">4</td>
<td align="center" valign="top">4</td>
<td align="left" valign="top">CHAR(10)</td>
<td align="left" valign="top">Program library</td>
</tr>
<tr>
<td align="center" valign="top">14</td>
<td align="center" valign="top">E</td>
<td align="left" valign="top">CHAR(10)</td>
<td align="left" valign="top">Program name</td>
</tr>
<tr>
<td align="center" valign="top">24</td>
<td align="center" valign="top">18</td>
<td align="left" valign="top">CHAR(1)</td>
<td align="left" valign="top">Multithreaded job action</td>
</tr>
<tr>
<td align="center" valign="top">25</td>
<td align="center" valign="top">19</td>
<td align="left" valign="top">CHAR(7)</td>
<td align="left" valign="top">Reserved</td>
</tr>
<tr>
<td align="center" valign="top">32</td>
<td align="center" valign="top">20</td>
<td align="left" valign="top">PP(*)</td>
<td align="left" valign="top">Procedure pointer to the exit procedure</td>
</tr>
</table>
<br>
<br>
<dl compact>
<dt><em><strong>Function type flag</strong></em></dt>
<dd>An unsigned integer that indicates whether the user-supplied exit program
that is called by <strong>Qp0lProcessSubtree()</strong> is a procedure or a
program. Valid values follow:
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em><strong>0</strong></em></td>
<td align="left" valign="top"><strong>QP0L_USER_FUNCTION_PTR:</strong> A user
procedure is called.</td>
</tr>
<tr>
<td align="left" valign="top"><em><strong>1</strong></em></td>
<td align="left" valign="top"><strong>QP0L_USER_FUNCTION_PGM:</strong> A user
program is called.</td>
</tr>
</table>
</dd>
<dt><em><strong>Multithreaded job action</strong></em></dt>
<dd>(Input) A CHAR(1) value that indicates the action to take in a
multithreaded job. The default value is QP0L_MLTTHDACN_SYSVAL. For release
compatibility and for processing this parameter against the QMLTTHDACN system
value, x'00, x'01', x'02', &amp; x'03' are treated as x'F0', x'F1', x'F2', and
x'F3'. Valid values follow:
<table cellpadding="5">
<!-- cols="10 90" -->
<tr>
<td align="left" valign="top"><em>x'00'</em></td>
<td align="left" valign="top">QP0L_MLTTHDACN_SYSVAL: The API evaluates the
QMLTTHDACN system value to determine the action to take in a multithreaded job.
Although the API can make repetitive calls to an exit program, the system value
is evaluated once before Qp0lProcessSubtree() issues its first exit program
call. This value is used on subsequent calls until the API returns control to
its caller. Valid QMLTTHDACN system values follow:
<table cellpadding="5">
<tr>
<td align="left" valign="top"><em>'1'</em></td>
<td align="left" valign="top">Call the exit program. Do not send an
informational message.</td>
</tr>
<tr>
<td align="left" valign="top"><em>'2'</em></td>
<td align="left" valign="top">Call the exit program. Send informational message
CPI3C80. Qp0lProcessSubtree() may call the exit program multiple times;
however, this message is sent only once for each call to
Qp0lProcessSubtree().</td>
</tr>
<tr>
<td align="left" valign="top"><em>'3'</em></td>
<td align="left" valign="top">The exit program is not called when the API
determines that it is running in a multithreaded job. ENOTSAFE is
returned.</td>
</tr>
</table>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>x'01'</em></td>
<td align="left" valign="top">QP0L_MLTTHDACN_NOMSG: Call the exit program. Do
not send an informational message.</td>
</tr>
<tr>
<td align="left" valign="top"><em>x'02'</em></td>
<td align="left" valign="top">QP0L_MLTTHDACN_MSG: Call the exit program. Send
informational message CPI3C80. Qp0lProcessSubtree() may call the exit program
multiple times; however, this message is sent only once for each call to
Qp0lProcessSubtree().</td>
</tr>
<tr>
<td align="left" valign="top"><em>x'03'</em></td>
<td align="left" valign="top">QP0L_MLTTHDACN_NO: The exit program is not called
when the API determines that it is running in a multithreaded job. ENOTSAFE is
returned.</td>
</tr>
</table>
</dd>
<dt><em><strong>Procedure pointer to the exit procedure</strong></em></dt>
<dd>A procedure pointer to the procedure that <strong>
Qp0lProcessSubtree()</strong> calls. This field must be NULL if a program is
called instead of a procedure.</dd>
<dt><em><strong>Program library</strong></em></dt>
<dd>The library in which the called program, identified by Program name, is
located. This field must be blank if a procedure is called instead of a
program.</dd>
<dt><em><strong>Program name</strong></em></dt>
<dd>The name of the program that is called. The program is located in the
library identified by Program library. This field must be blank if a procedure
is called instead of a program.</dd>
<dt><em><strong>Reserved</strong></em></dt>
<dd>A reserved field. This field must be set to binary zero.</dd>
</dl>
<br>
<br>
</dd>
<dt><strong><em>Function_CtlBlk_ptr</em></strong></dt>
<dd>(Input) A pointer that <strong>Qp0lProcessSubtree()</strong> passes to the
user-defined exit program that is called. <strong>Qp0lProcessSubtree()</strong>
does not process this pointer or what is referred to by the pointer. It passes
the pointer as a parameter to the user-defined exit program that was specified.
This is a means for the caller of <strong>Qp0lProcessSubtree()</strong> to pass
information to and from the Process a Path Name exit program.</dd>
</dl>
<br>
<h3>Authorities</h3>
<p><strong>Note</strong>: Adopted authority is not used.</p>
<p><strong><a name="TBLASWP1P">Authorization Required for
Qp0lProcessSubtree()</a></strong></p>
<table border>
<!-- cols="60 20 20" -->
<tr>
<th align="left" valign="bottom">Object Referred to</th>
<th align="left" valign="bottom">Authority Required</th>
<th align="left" valign="bottom">errno</th>
</tr>
<tr>
<td align="left" valign="top" width="90%">Each directory, preceding the last
component, in a <em>Path Name</em></td>
<td align="left" valign="top" width="5%">*X</td>
<td align="left" valign="top" width="5%">EACCES</td>
</tr>
<tr>
<td align="left" valign="top">The <em>Path Name</em> directory and all
subdirectories of the <em>Path Name</em> that are included in the search.</td>
<td align="left" valign="top">*RX (See <strong> Note</strong>)</td>
<td align="left" valign="top">EACCES</td>
</tr>
<tr>
<td align="left" valign="top">Each directory, preceding the last component, in
any path name pointed to by the <em>IN_EXclusion ptr</em></td>
<td align="left" valign="top">*X</td>
<td align="left" valign="top">EACCES</td>
</tr>
<tr>
<td align="left" valign="top">The <em>Path Name</em> directory and all
subdirectories of any path name pointed to by an inclusive list</td>
<td align="left" valign="top">*RX (See <strong> Note</strong>)</td>
<td align="left" valign="top">EACCES</td>
</tr>
<tr>
<td align="left" valign="top">The object identified by the path name that is passed to the exit program, if the object is a user profile (*USRPRF)</td>
<td align="left" valign="top">Any authority greater than *EXCLUDE</td>
<td align="left" valign="top">EACCES</td>
</tr>
<tr>
<td align="left" valign="top">Any called program pointed to by the <em>
UserFunction_ptr</em> parameter</td>
<td align="left" valign="top">*X</td>
<td align="left" valign="top">EACCES</td>
</tr>
<tr>
<td align="left" valign="top">Any library that contains the called program
pointed to by the <em>UserFunction_ptr</em> parameter</td>
<td align="left" valign="top">*X</td>
<td align="left" valign="top">EACCES</td>
</tr>
<tr>
<td align="left" valign="top"><strong>Note:</strong> If the directory or subdirectories have no objects in
them, only *R is required.
</td>
</tr>
</table>
<br>
<br>
<h3>Return Value</h3>
<table cellpadding="5">
<!-- cols="5 95" -->
<tr>
<td align="left" valign="top"><em>0</em></td>
<td align="left" valign="top"><strong>Qp0lProcessSubtree()</strong> was
successful.</td>
</tr>
<tr>
<td align="left" valign="top"><em>-1</em></td>
<td align="left" valign="top"><strong>Qp0lProcessSubtree()</strong> was not
successful. The <em>errno</em> variable is set to indicate the error.</td>
</tr>
</table>
<br>
<br>
<h3>Error Conditions</h3>
<p>If <strong>Qp0lProcessSubtree()</strong> is not successful, the <em>
errno</em> indicates one of the following errors:</p>
<table cellpadding="5">
<!-- cols="25 75" -->
<tr>
<th align="left" valign="bottom">Error condition</th>
<th align="left" valign="bottom">Additional information</th>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EACCES">EACCES</a>]</em></td>
<td align="left" valign="top">
<p>If you are accessing a remote file through the Network File System, update
operations to file permissions at the server are not reflected at the client
until updates to data that is stored locally by the Network File System take
place. (Several options on the Add Mounted File System (ADDMFS) command
determine the time between refresh operations of local data.) Access to a
remote file may also fail due to different mappings of user IDs (UID) or group
IDs (GID) on the local and remote systems.</p>
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EAGAIN">EAGAIN</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EBADNAME">EBADNAME</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EBUSY">EBUSY</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EDAMAGE">EDAMAGE</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EFAULT">EFAULT</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EINVAL">EINVAL</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EIO">EIO</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EISDIR">EISDIR</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ELOOP">ELOOP</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EMFILE">EMFILE</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENAMETOOLONG">ENAMETOOLONG</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENFILE">ENFILE</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOENT">ENOENT</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOMEM">ENOMEM</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOSPC">ENOSPC</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOSYSRSC">ENOSYSRSC</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOTAVAIL">ENOTAVAIL</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOTDIR">ENOTDIR</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#ENOTSAFE">ENOTSAFE</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
<tr>
<td align="left" valign="top"><em>[<a href="unix14.htm#EUNKNOWN">EUNKNOWN</a>]</em></td>
<td align="left" valign="top">
&nbsp;
</td>
</tr>
</table>
<br>
<br>
<h3>Error Messages</h3>
<p>The following message may be sent from this function:</p>
<table width="100%" cellpadding="5">
<!-- cols="15 85" -->
<tr>
<th align="left" valign="top">Message ID</th>
<th align="left" valign="top">Error Message Text</th>
</tr>
<tr>
<td align="left" valign="top">CPE3418 E</td>
<td align="left" valign="top">Possible APAR condition or hardware failure.</td>
</tr>
<tr>
<td align="left" valign="top">CPF3CF2 E</td>
<td align="left" valign="top">Error(s) occurred during running of &amp;1
API.</td>
</tr>
<tr>
<td align="left" valign="top">CPFA0D4 E</td>
<td align="left" valign="top">File system error occurred. Error number
&amp;1.</td>
</tr>
<tr>
<td align="left" valign="top">CPF9872 E</td>
<td align="left" valign="top">Program or service program &amp;1 in library
&amp;2 ended. Reason code &amp;3.</td>
</tr>
</table>
<br>
<br>
<h3><a name="USAGE">Usage Notes</a></h3>
<ol>
<li>This function will fail with error code [ENOTSAFE] when all the following
conditions are true:
<ul>
<li>Where multiple threads exist in the job.<br>
<br>
</li>
<li>The object on which this function is operating resides in a file system
that is not threadsafe. Only the following file systems are threadsafe for this
function:
<ul>
<li>"Root" (/)</li>
<li>QOpenSys</li>
<li>User-defined</li>
<li>QNTC</li>
<li>QSYS.LIB</li>
<li>Independent ASP QSYS.LIB</li>
<li>QOPT</li>
<li>Network File System</li>
<li>QFileSvr.400</li>
</ul>
</li>
</ul>
<br>
<br>
</li>
<li>If the exit program called by <strong>Qp0lProcessSubtree()</strong> is not
threadsafe or uses a function that is not threadsafe, then <strong>
Qp0lProcessSubtree()</strong> is not threadsafe.<br>
<br>
</li>
<li>If the exit program called by <strong>Qp0lProcessSubtree()</strong> uses a
function that fails when there are secondary threads active in the job,
<strong>Qp0lProcessSubtree()</strong> may fail as a result.<br>
<br>
</li>
<li>Basic function and usage considerations<br>
<br>
<ul>
<li><strong>Qp0lProcessSubtree()</strong> does not perform the following tasks
but is designed to work with the user exit function and other APIs to be useful
in accomplishing the following and other tasks:
<ul compact>
<li>Retrieve object attributes (like authorities, dates, or sizes).</li>
<li>Build lists from selected objects.</li>
<li>Delete directories.</li>
<li>Identify multiple occurrences of an object within or across
directories.</li>
<li>Count the number of objects in a directory.</li>
</ul>
<br>
<br>
</li>
<li><strong>DosSetRelMaxFH()</strong> is called to increase to the maximum the
number of file descriptors that can be opened during processing such that
<strong>Qp0lProcessSubtree()</strong> is not likely to fail due to a lack of
descriptors. This value is not reset when <strong>Qp0lProcessSubtree()</strong>
ends because the API could be running in a multithreaded job.</li>
</ul>
<br>
<br>
</li>
<li>Object locking
<p><strong>Qp0lProcessSubtree()</strong> does not perform any object locking,
other than what is done when opening a directory to read the objects it
contains, so that the exit program does not encounter or need to manage locks
held by <strong>Qp0lProcessSubtree()</strong>.
<p>If <strong>Qp0lProcessSubtree()</strong> encounters a directory that is
locked, <strong>Qp0lProcessSubtree()</strong> uses the defined
Err_recovery_action to determine how to handle the locked condition. Locks on
objects that are not directories have no effect on <strong>
Qp0lProcessSubtree()</strong>.</p>
<br>
</li>
<li><img src="delta.gif" alt="Start of change">Search Results
<p>Once <strong>Qp0lProcessSubtree()</strong> has started searching a path,
its search results may be affected by operations that update the organization of
objects within the specifed directory tree. This includes but is not limited to
the following:
<ul>
<li>Adding, removing, or renaming object links,
<li>Mounting or unmounting file systems,
<li>Updating the effective root directory for the process calling this API,
<li>Updating the contents of a symbolic link.
</ul>
<img src="deltaend.gif" alt="End of change">
<br>
<br>
</li>
<li>Design considerations for parameters<br>
<br>
<ul>
<li>Symbolic links
<p>When the last component of the path name supplied on the initial call of
<strong>Qp0lProcessSubtree()</strong> is a symbolic link, <strong>
Qp0lProcessSubtree()</strong> resolves and follows the initial link to its
target and performs its normal functions on the target. All other symbolic
links that are encountered in the same search are not resolved to their
targets.</p>
<p>If the path name supplied on the initial call of <strong>
Qp0lProcessSubtree()</strong> is a symbolic link that points to another file
system or that points to a remote file system, the API resolves and processes
the initial link only. It does not resolve other symbolic links that are
encountered in the same search. However, if the caller specified that remote
objects are not processed, but the initial path name (whether a symbolic link
or not) points to a remote file system, the link is not resolved. <strong>
Qp0lProcessSubtree()</strong> calls the exit program with a NULL path name and
an indicator that <strong>Qp0lProcessSubtree()</strong> has completed
successfully without any error indicators to the exit program.</p>
<p>When *SYMLNK is specified as part of the selection criteria, <strong>
Qp0lProcessSubtree()</strong> does not resolve the selected names.</p>
</li>
<li>Recovery Actions
<p>There are three separate parameters that control error recovery during a
search. The caller of the API determines how an error should be reported to the
exit program by setting the <em>Err_recovery_actions</em> parameter. The API
sets the <em>Selection status pointer</em> and sends it to the exit program to
indicate one of four conditions: the API search status is OK, the last object
has been processed, the API has encountered recoverable errors, or the search
cannot continue. For error conditions it also sends a valid <em>errno</em>. The
exit program returns an indicator back to the API either to continue or to end
the search by setting the <em>Return value pointer</em>. For error conditions,
it also returns a valid <em>errno</em>, pointed to by the <em>Return value
pointer</em>. Each time <strong>Qp0lProcessSubtree()</strong> regains control
from the exit program, it determines whether the search should continue or end
by evaluating the <em>Err_recovery_actions</em> parameter, its <em>Selection
status pointer</em>, and the <em>Return value pointer</em>. Upon ending,
<strong>Qp0lProcessSubtree()</strong> returns 0 to indicate a successful
search, or a -1 and an <em>errno</em> to indicate the error condition. This
<em>errno</em> may have been set by the exit program (<em>Return value
pointer</em>).</p>
<p>This error recovery design allows for flexibility in handling errors between
the caller, the API, and the exit program. Whenever an unrecoverable error
occurs, if possible, the exit program is given a final call; this call allows
the exit program to do such tasks as cleanup or to put information in the
function control block, or to record information about the error. However, the
exit program cannot decide that the search should continue. The API will return
to its caller when it regains control. There are only two specific instances in
which the API determines that the exit program is not called:</p>
<ul>
<li>When the API cannot resolve the exit program name or its authorization.<br>
<br>
</li>
<li>When input parameters are missing or specified incorrectly. (The API
returns EINVAL to the caller before any other processing.)</li>
</ul>
<p>Following is a diagram showing the flow and relationship of these
parameters.</p>
</li>
</ul>
</li>
</ol>
<p align="center"><img src="RBAFX598.gif" alt=
"Diagram showing the flow and relationship of the input and output parameters">
</p>
<br>
<h3>Scenarios</h3>
<p>Following are scenarios showing calls and the results of calls to <strong>
Qp0lProcessSubtree()</strong>. <a href="#FIGRV4F004">Directory Structure A</a>
and <a href="#FIGRV4F003">Directory Structure B</a> define the input directory
structure for these scenarios.</p>
<h3><a name="FIGRV4F004">Figure: Directory Structure A</a></h3>
<p align="center"><img src="RV4F004.GIF" alt=
"A directory structure representing three subdirectories, three objects, and a symbolic link.">
</p>
<p>This directory structure represents three subdirectories (a, b, c), three
objects (x, y, z), and a symbolic link (t).</p>
<br>
<h3><a name="FIGRV4F003">Figure: Directory Structure B</a></h3>
<p align="center"><img src="RV4F003.GIF" alt=
"A directory structure representing six subdirectories and seven objects."></p>
<p>This directory structure represents six subdirectories (a, b, c, d, e, f)
and seven objects (t, u, v, w, x, y, z).</p>
<br>
<h3><a name="HDREXAM1">Scenario 1</a></h3>
<p>This scenario assumes processing a directory as shown by <em>Directory
Structure A</em> in <a href="#FIGRV4F004">Figure above</a>.</p>
<p>This scenario shows a call to the API without any criteria to filter the
selection of objects in the path being searched. If the API call were coded
with the parameter values as shown by <em>Input value</em> in <a href=
"#TBLSW1TAB">Scenario 1 API Input</a>, the exit program would be called nine
times and would pass the object names as shown by the <em>Object Name
Pointer</em> in <a href="#TBLSW2TAB">Results of a call</a>. Because
QP0L_SUBTREE_YES is specified, all of the directories in the path will be
opened and the name of all the objects that they contain will be passed to the
exit program. Note that the only guaranteed order is that parent directories
are passed to the exit program after all of their children.<br>
</p>
<h3><a name="TBLSW1TAB">Figure: Scenario 1 API Input</a></h3>
<table border cellpadding="5">
<!-- cols="25 75" -->
<tr>
<th align="left" valign="bottom">Input Parameter</th>
<th align="left" valign="bottom">Input value</th>
</tr>
<tr>
<td align="left" valign="top">*Path_Name</td>
<td align="left" valign="top">'/' ('/' processes every directory on the system
and is not recommended if performance is a consideration)</td>
</tr>
<tr>
<td align="left" valign="top">Subtree_level</td>
<td align="left" valign="top">QP0L_SUBTREE_YES</td>
</tr>
<tr>
<td align="left" valign="top">*Objtypes_array_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
<tr>
<td align="left" valign="top">Local_remote_obj</td>
<td align="left" valign="top">QP0L_LOCAL_REMOTE_OBJ</td>
</tr>
<tr>
<td align="left" valign="top">*IN_EXclusion_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
<tr>
<td align="left" valign="top">Err_recovery_action</td>
<td align="left" valign="top">QP0L_PASS_WITH_ERRORID</td>
</tr>
<tr>
<td align="left" valign="top">*UserFunction_ptr</td>
<td align="left" valign="top">QP0L_USER_FUNCTION_PTR</td>
</tr>
<tr>
<td align="left" valign="top">*Function_CtlBlk_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
</table>
<br>
<h3><a name="TBLSW2TAB">Figure: Results of a call</a></h3>
<table border cellpadding="5">
<!-- cols="15 85" -->
<tr>
<th align="left" valign="bottom">Exit Program Call Count</th>
<th align="left" valign="bottom">Object Name Pointer</th>
</tr>
<tr>
<td align="left" valign="top">1</td>
<td align="left" valign="top">/a/b/y</td>
</tr>
<tr>
<td align="left" valign="top">2</td>
<td align="left" valign="top">/a/b</td>
</tr>
<tr>
<td align="left" valign="top">3</td>
<td align="left" valign="top">/a/x</td>
</tr>
<tr>
<td align="left" valign="top">4</td>
<td align="left" valign="top">/a/t</td>
</tr>
<tr>
<td align="left" valign="top">5</td>
<td align="left" valign="top">/a/c/z</td>
</tr>
<tr>
<td align="left" valign="top">6</td>
<td align="left" valign="top">/a/c</td>
</tr>
<tr>
<td align="left" valign="top">7</td>
<td align="left" valign="top">/a</td>
</tr>
<tr>
<td align="left" valign="top">8</td>
<td align="left" valign="top">/</td>
</tr>
<tr>
<td align="left" valign="top">9</td>
<td align="left" valign="top">NULL path name (indicates the API completed)</td>
</tr>
</table>
<br>
<br>
<h3><a name="HDREXAM2">Scenario 2</a></h3>
<p>This scenario assumes processing a directory as shown by <em>Directory
Structure A</em> in the <a href="#FIGRV4F004">Figure above</a>.</p>
<p>This shows a call to the API with the <em>Subtree level</em> parameter set
to retrieve only one level, without any object filtering. Since QP0L_SUBTREE_NO
is specified, the names of all objects in the path will be passed to the exit
program, however, none of the directories will be opened. This allows a caller
to perform tasks such as identifying all of the root objects for a file system.
For example, this would identify all of the first level folders, when
processing against the QDLS file system. Then the API can be called recursively
from within the exit program, with each of these folders specified as the path
to be searched.</p>
<p>If the API call were coded with the parameter values as shown by <em>Input
value</em> in <a href="#TBLSW3TAB">Scenario 2 API Input</a>, the exit program
would be called six times and would pass the object names as shown by the <em>
Object Name Pointer</em> in <a href="#TBLSW4TAB">Results of a call</a>.<br>
</p>
<br>
<h3><a name="TBLSW3TAB">Figure: Scenario 2 API Input</a></h3>
<table border cellpadding="5">
<!-- cols="25 75" -->
<tr>
<th align="left" valign="bottom">Input Parameter</th>
<th align="left" valign="bottom">Input value</th>
</tr>
<tr>
<td align="left" valign="top">*Path_Name</td>
<td align="left" valign="top">'/a'</td>
</tr>
<tr>
<td align="left" valign="top">Subtree_level</td>
<td align="left" valign="top">QP0L_SUBTREE_NO</td>
</tr>
<tr>
<td align="left" valign="top">*Objtypes_array_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
<tr>
<td align="left" valign="top">Local_remote_obj</td>
<td align="left" valign="top">QP0L_LOCAL_REMOTE_OBJ</td>
</tr>
<tr>
<td align="left" valign="top">*IN_EXclusion_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
<tr>
<td align="left" valign="top">Err_recovery_action</td>
<td align="left" valign="top">QP0L_PASS_WITH_ERRORID</td>
</tr>
<tr>
<td align="left" valign="top">*UserFunction_ptr</td>
<td align="left" valign="top">QP0L_USER_FUNCTION_PTR</td>
</tr>
<tr>
<td align="left" valign="top">*Function_CtlBlk_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
</table>
<br>
<br>
<h3><a name="TBLSW4TAB">Figure: Results of a call</a></h3>
<table border cellpadding="5">
<!-- cols="15 85" -->
<tr>
<th align="left" valign="bottom">Exit Program Call Count</th>
<th align="left" valign="bottom">Object Name Pointer</th>
</tr>
<tr>
<td align="left" valign="top">1</td>
<td align="left" valign="top">/a/b</td>
</tr>
<tr>
<td align="left" valign="top">2</td>
<td align="left" valign="top">/a/x</td>
</tr>
<tr>
<td align="left" valign="top">3</td>
<td align="left" valign="top">/a/t</td>
</tr>
<tr>
<td align="left" valign="top">4</td>
<td align="left" valign="top">/a/c</td>
</tr>
<tr>
<td align="left" valign="top">5</td>
<td align="left" valign="top">/a</td>
</tr>
<tr>
<td align="left" valign="top">6</td>
<td align="left" valign="top">NULL path name (indicates the API completed)</td>
</tr>
</table>
<br>
<br>
<h3><a name="HDREXAM3">Scenario 3</a></h3>
<p>This scenario assumes processing a directory as shown by <em>Directory
Structure B</em> in the <a href="#FIGRV4F003">Figure above</a>.</p>
<p>This scenario represents a call to the API with an inclusion list. Note that
the <em>Path Name</em> parameter is not used as the starting directory since
each entry in an inclusion list is treated as a starting directory.</p>
<p>If the API call were coded with the parameter values as shown by <em>Input
value</em> in <a href="#TBLSW5TAB">Scenario 3 API Input</a>, the exit program
would be called six times and would pass the object names as shown by the <em>
Object Name Pointer</em> in <a href="#TBLSW6TAB">Results of a call</a>.</p>
<p>Note that /a/b/c/d/v could be returned before /a/b/c/d/u, as shown in this
scenario, since children in a directory can be returned in any order. The only
guaranteed order is that the exit program is called with all children objects
before being called with the parent to allow the exit program to delete
directories if desired.</p>
<br>
<h3><a name="TBLSW5TAB">Figure: Scenario 3 API Input</a></h3>
<table border cellpadding="5">
<!-- cols="25 75" -->
<tr>
<th align="left" valign="bottom">Input Parameter</th>
<th align="left" valign="bottom">Input value</th>
</tr>
<tr>
<td align="left" valign="top">*Path_Name</td>
<td align="left" valign="top">NULL (not used with an inclusion list)</td>
</tr>
<tr>
<td align="left" valign="top">Subtree_level</td>
<td align="left" valign="top">QP0L_SUBTREE_YES</td>
</tr>
<tr>
<td align="left" valign="top">*Objtypes_array_ptr</td>
<td align="left" valign="top">'*DIR ' '*STMF '<br>
</td>
</tr>
<tr>
<td align="left" valign="top">Local_remote_obj</td>
<td align="left" valign="top">QP0L_LOCAL_OBJ</td>
</tr>
<tr>
<td align="left" valign="top">*IN_EXclusion_ptr</td>
<td align="left" valign="top">QP0L_INCLUSION_TYPE, '/a/b/c/d/' '/a/b/c/e/'</td>
</tr>
<tr>
<td align="left" valign="top">Err_recovery_action</td>
<td align="left" valign="top">QP0L_PASS_WITH_ERRORID</td>
</tr>
<tr>
<td align="left" valign="top">*UserFunction_ptr</td>
<td align="left" valign="top">QP0L_USER_FUNCTION_PTR</td>
</tr>
<tr>
<td align="left" valign="top">*Function_CtlBlk_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
</table>
<br>
<br>
<h3><a name="TBLSW6TAB">Figure: Results of a call</a></h3>
<table border cellpadding="5">
<!-- cols="15 85" -->
<tr>
<th align="left" valign="bottom">Exit Program Call Count</th>
<th align="left" valign="bottom">Object Name Pointer</th>
</tr>
<tr>
<td align="left" valign="top">1</td>
<td align="left" valign="top">/a/b/c/d/v</td>
</tr>
<tr>
<td align="left" valign="top">2</td>
<td align="left" valign="top">/a/b/c/d/u</td>
</tr>
<tr>
<td align="left" valign="top">3</td>
<td align="left" valign="top">/a/b/c/d</td>
</tr>
<tr>
<td align="left" valign="top">4</td>
<td align="left" valign="top">/a/b/c/e/w</td>
</tr>
<tr>
<td align="left" valign="top">5</td>
<td align="left" valign="top">/a/b/c/e/</td>
</tr>
<tr>
<td align="left" valign="top">6</td>
<td align="left" valign="top">NULL path name (indicates the API completed)</td>
</tr>
</table>
<br>
<br>
<h3><a name="HDREXAM4">Scenario 4</a></h3>
<p>This scenario assumes processing a directory as shown by <em>Directory
Structure B</em> in the <a href="#FIGRV4F003">Figure above</a>.</p>
<p>This scenario represents a call to the API with an exclusion list. Note that
each relative entry in the exclusion list is resolved relative to the current
working directory at the time the API is called. This scenario assumes that the
current working directory is /a/b/.</p>
<p>If the API call were coded with the parameter values as shown by <em>Input
value</em> in <a href="#TBLSW7TAB">Scenario 4 API Input</a>, the exit program
would be called eight times and would pass the object names as shown by the
<em>Object Name Pointer</em> in <a href="#TBLSW8TAB">Results of a call</a>.</p>
<p>This scenario also shows that children in a directory can be returned in any
order. The only guaranteed order is that the exit program is called with all
children objects before being called with the parent to allow the exit program
to delete directories if desired.</p>
<br>
<h3><a name="TBLSW7TAB">Figure: Scenario 4 API Input</a></h3>
<table border cellpadding="5">
<!-- cols="25 75" -->
<tr>
<th align="left" valign="bottom">Input Parameter</th>
<th align="left" valign="bottom">Input value</th>
</tr>
<tr>
<td align="left" valign="top">*Path_Name</td>
<td align="left" valign="top">'/a/b/'</td>
</tr>
<tr>
<td align="left" valign="top">Subtree_level</td>
<td align="left" valign="top">QP0L_SUBTREE_YES</td>
</tr>
<tr>
<td align="left" valign="top">*Objtypes_array_ptr</td>
<td align="left" valign="top">'*DIR ' '*STMF '<br>
</td>
</tr>
<tr>
<td align="left" valign="top">Local_remote_obj</td>
<td align="left" valign="top">QP0L_LOCAL_OBJ</td>
</tr>
<tr>
<td align="left" valign="top">*IN_EXclusion_ptr</td>
<td align="left" valign="top">QP0L_EXCLUSION_TYPE, 'c/d/' 'c/e/'</td>
</tr>
<tr>
<td align="left" valign="top">Err_recovery_action</td>
<td align="left" valign="top">QP0L_PASS_WITH_ERRORID</td>
</tr>
<tr>
<td align="left" valign="top">*UserFunction_ptr</td>
<td align="left" valign="top">QP0L_USER_FUNCTION_PTR</td>
</tr>
<tr>
<td align="left" valign="top">*Function_CtlBlk_ptr</td>
<td align="left" valign="top">NULL</td>
</tr>
</table>
<br>
<br>
<h3><a name="TBLSW8TAB">Figure: Results of a call</a></h3>
<table border cellpadding="5">
<!-- cols="15 85" -->
<tr>
<th align="left" valign="bottom">Exit Program Call Count</th>
<th align="left" valign="bottom">Object Name Pointer</th>
</tr>
<tr>
<td align="left" valign="top">1</td>
<td align="left" valign="top">/a/b/t</td>
</tr>
<tr>
<td align="left" valign="top">2</td>
<td align="left" valign="top">/a/b/c/y</td>
</tr>
<tr>
<td align="left" valign="top">3</td>
<td align="left" valign="top">/a/b/c/f/z</td>
</tr>
<tr>
<td align="left" valign="top">4</td>
<td align="left" valign="top">/a/b/c/f</td>
</tr>
<tr>
<td align="left" valign="top">5</td>
<td align="left" valign="top">/a/b/c/x</td>
</tr>
<tr>
<td align="left" valign="top">6</td>
<td align="left" valign="top">/a/b/c</td>
</tr>
<tr>
<td align="left" valign="top">7</td>
<td align="left" valign="top">/a/b</td>
</tr>
<tr>
<td align="left" valign="top">8</td>
<td align="left" valign="top">NULL path name (indicates the API completed)</td>
</tr>
</table>
<br>
<br>
<h3>Related Information</h3>
<ul>
<li>The &lt;<strong>Qp0lstdi.h</strong>&gt; file (see <a href="unix13.htm">
Header Files for UNIX-Type Functions</a>)
</li>
<li>The &lt;<strong>qlg.h</strong>&gt; file (see <a href="unix13.htm">Header
Files for UNIX-Type Functions</a>)
</li>
<li><a href="qprstreeu.htm">QlgProcessSubtree()</a>--Process a Path Name (using
NLS-enabled path name)
</li>
<li><a href="xprstree.htm">Process a Path Name Exit Program</a></li>
</ul>
<br>
<h3>Example</h3>
<p>See <a href="../apiref/aboutapis.htm#codedisclaimer">Code disclaimer information</a>
for information pertaining to code examples.</p>
<p>Following is a code example showing a call to the Qp0lProcessSubtree() API
with a procedure as the exit program:</p>
<pre>
/*****************************************************************/
/*****************************************************************/
#include &lt;Qp0lstdi.h&gt;
#include &lt;stdio.h&gt;
#include &lt;errno.h&gt;
#include &lt;qtqiconv.h&gt;
void Obj_Print_Function
(uint *Selection_status_pointer,
uint *Error_value_pointer,
uint *Return_value_pointer,
Qlg_Path_Name_T *Object_name_pointer,
void *Function_control_block_pointer)
{
/****************************************************************/
/* This exit program example prints the names, one at a time, */
/* of each entry in a directory structure that it receives on */
/* each call from Qp0lProcessSubtree(). */
/****************************************************************/
#define PATH_TYPE_POINTER 0x00000001 /* If this flag is on, */
/* the qlg structure contains a */
/* pointer to the path name. */
/* Otherwise, the path name is in */
/* contiguous storage within the */
/* qlg structure. */
typedef union pn_input_type
{
char pn_char_type[256]; /* path name is in */
/* contiguous storage */
char *pn_ptr_type; /* path name is a pointer */
};
typedef struct pnstruct
{
Qlg_Path_Name_T qlg_struct;
union pn_input_type pn;
};
struct pnstruct *pns;
char *path_ptr;
size_t insz;
size_t outsz = 1000;
char outbuf[1000];
char *outbuf_ptr;
iconv_t cd;
size_t ret_iconv;
QtqCode_T toCode = {37,0,0,0,0,0};
QtqCode_T fromCode = {61952,0,0,1,0,0};
if (*Selection_status_pointer == QP0L_SELECT_OK)
{
if (Object_name_pointer != NULL)
{
/************************************************************/
/* Point to the pathname and get the size of the pathname */
/* that was sent from the Qp0lProcessSubtree() API. The */
/* format of the pathname must be determined by evaluating */
/* Path_Type in the qlg structure. */
/************************************************************/
pns = (struct pnstruct *)Object_name_pointer;
if (Object_name_pointer-&gt;Path_Type &amp; PATH_TYPE_POINTER)
{
path_ptr = pns-&gt;pn.pn_ptr_type;
}
else
{
path_ptr = (char *)(pns-&gt;pn.pn_char_type);
}
insz = pns-&gt;qlg_struct.Path_Length;
/************************************************************/
/* Initialize the print buffer. */
/************************************************************/
outbuf_ptr = (char *)outbuf;
memset(outbuf_ptr, 0x00, insz);
/************************************************************/
/* Use iconv to convert from 61952 to the job CCSID. */
/* REMEMBER iconv will change the data that it receives. */
/************************************************************/
cd = /* Open the conversion descriptor.*/
QtqIconvOpen(&amp;toCode,
&amp;fromCode);
if (cd.return_value == -1)
{
/*********************************************************/
/* If conversion descriptor was not opened successfully, */
/* return an error and errno (ECONVERT) to the API. */
/*********************************************************/
*Return_value_pointer = errno;
return;
}
ret_iconv = /* Perform the conversion.*/
(iconv(cd,
(char **)&amp;(path_ptr),
&amp;insz,
(char **)&amp;(outbuf_ptr),
&amp;outsz));
if (ret_iconv != 0)
{
/*********************************************************/
/* If the conversion failed, close the conversion */
/* descriptor and return an error and errno (ECONVERT) */
/* to the API. */
/*********************************************************/
ret_iconv= iconv_close(cd);
*Return_value_pointer = errno;
return;
}
/************************************************************/
/* Print the name of the object being processed and close */
/* the conversion descriptor. */
/************************************************************/
printf(&quot;In User Exit Program. Path is %s.\n&quot;, outbuf);
ret_iconv = iconv_close(cd);
} /* end Object_name_pointer != NULL */
else
{
printf(&quot;In User Exit Program with a null Pathname \n&quot;);
}
} /* end *Selection_status_pointer == QP0L_SELECT_OK */
*Return_value_pointer = 0;
} /* end Exit program */
int main (int argc, char *argv[])
{
#define MYPN &quot;/TestDir&quot;
const int zero = 0;
const char US_const[3]= &quot;US&quot;;
const char Language_const[4]=&quot;ENU&quot;;
const char Path_Name_Del_const[2]= &quot;/&quot;;
const char LibObj_const[12]= &quot;*LIB &quot;;
typedef struct pnstruct
{
Qlg_Path_Name_T qlg_struct;
char pn[50]; /* Must be greater than */
/* or equal the length */
/* of the path name. */
};
struct pnstruct pns;
Qp0l_Objtypes_List_t MyObj_types;
Qp0l_User_Function_t User_function;
struct
{
uint AnyData_to_the_exitprogram;
uint AnyData_not_processed_by_the_API;
} CtlBlkAreaName;
int rc;
/***************************************************************/
/* In this example, the pathname is defined by MYPN as TestDir */
/* and it is assumed that the TestDir directory exists on the */
/* system. Various other functions or other routines could be */
/* included here to (for example): */
/* 1) determine the beginning search directory. */
/* 2) construct the path name in the correct format. */
/* 3) others... */
/***************************************************************/
/***************************************************************/
/***************************************************************/
/* Initialize Qp0lProcessSubtree() API Parameters */
/***************************************************************/
memset((void*)&amp;pns, 0x00, sizeof(struct pnstruct));
pns.qlg_struct.CCSID = 37;
memcpy(pns.qlg_struct.Country_ID,US_const,2);
memcpy(pns.qlg_struct.Language_ID,Language_const,3);
pns.qlg_struct.Path_Type = zero;
pns.qlg_struct.Path_Length = sizeof(MYPN)-1;
memcpy(pns.qlg_struct.Path_Name_Delimiter,Path_Name_Del_const,1);
memcpy(pns.pn,MYPN,sizeof(MYPN));
MyObj_types.Number_Of_Objtypes = zero;
memset((void *)&amp;User_function, 0x00, sizeof(Qp0l_User_Function_t));
User_function.Function_Type = QP0L_USER_FUNCTION_PTR;
User_function.Mltthdacn[0] = QP0L_MLTTHDACN_NOMSG;
User_function.Procedure = &amp;Obj_Print_Function;
if (rc = Qp0lProcessSubtree((Qlg_Path_Name_T *)&amp;pns,
QP0L_SUBTREE_YES,
(Qp0l_Objtypes_List_t *)NULL,
QP0L_LOCAL_REMOTE_OBJ,
(Qp0l_IN_EXclusion_List_t *)NULL,
QP0L_PASS_WITH_ERRORID,
&amp;User_function,
&amp;CtlBlkAreaName) == 0)
{
printf(&quot;Qp0lProcessSubtree() Successful : error = %d\n&quot;, errno);
}
else
{/*unsuccessful return from Qp0lProcessSubtree() API */
printf(&quot;ERROR on Qp0lProcessSubtree(): error = %d\n&quot;, errno);
perror(&quot;Error message&quot;);
}
} /* end main */
</pre>
<br>
<hr>
API introduced: V4R3
<hr>
<center>
<table cellpadding="2" cellspacing="2">
<tr align="center">
<td valign="middle" align="center"><a href="#Top_Of_Page">Top</a> | <a href=
"unix.htm">UNIX-Type APIs</a> | <a href="aplist.htm">APIs by category</a></td>
</tr>
</table>
</center>
</body>
</html>