第八章运行程序.docx
- 文档编号:6324583
- 上传时间:2023-05-09
- 格式:DOCX
- 页数:22
- 大小:29.84KB
第八章运行程序.docx
《第八章运行程序.docx》由会员分享,可在线阅读,更多相关《第八章运行程序.docx(22页珍藏版)》请在冰点文库上搜索。
第八章运行程序
2.5第八章运行程序
本章讲述了以下内容:
使用CLCALL命令运行程序和传递参数
从菜单驱动的应用程序运行程序
使用用户建立的命令运行程序
管理活动组
管理运行时存储空间
另外,可以用以下方法运行程序
程序员菜单。
CL程序设计包含此菜单的信息,启动应用开发管理工具(STRPDM)命令。
ADTS/400:
应用开发管理工具包含这条命令的信息。
QCMDEXC程序。
CL程序设计包含这个程序的信息。
高级语言。
第九章2.6节中的“程序和过程调用”。
提供了从其它高级语言运行程序及调用程序和过程的资料。
2.5.1使用CLCALL命令运行程序
可以使用CLCALL命令运行程序(类型为*PGM)。
可以交互地或作为批处理作业的一部分,或在CL程序中使用该命令。
如果需要提示,键入CALL然后按F4(提示)键。
如果需要帮助,键入CALL然后按F1(帮助)键。
例如:
要从命令行调用程序EMPRPT,键入:
CALLEMPRPT
指定的程序目标必须在某个库中,并且这个库要包含在库列表*LIBL中。
也可以象下面那样在CLCALL命令中确切地指出库名:
CALLMYLIB/EMPRPT
关于CLCALL命令的详细的资料参见CL参考手册。
一旦调用程序,OS/400系统就执行程序中的指令。
2.5.1.1使用CLCALL命令传递参数
当运行程序时,使用CLCALL命令的PARM选项来向ILE程序传递参数。
CALLPGM(程序名)
PARM(参数1,参数2,……,参数n)
也可以只键入参数而不指定键字。
CALL库/程序名(参数1,参数2,……,参数n)
每个参数的值可以由CL程序变量或由以下之一来指定:
字符串常量
数字常量
逻辑常量
如果把参数传递给一个ILERPG/400过程,这个过程作为入口过程,那么这个程序必须有且仅有一个*ENTRYPLIST。
紧随其后的参数(在PARM语句中)必须与CALL命令所传递的参数一一对应。
关于如何处理参数的完整性描述参见CL参考手册中的CALL命令或CL程序设计中的“在程序间传递参数”。
例如,程序EMPRPT2在首次起动时要求有正确的口令传递给它,否则将不运行。
图30显示了源程序。
1.要建立程序,键入:
CRTBNDRPGPGM(MYLIB/EMPRPT2)
2.要运行程序,键入:
CALLMYLIB/EMPRPT2(HELLO)
当调用命令发出时,由命令传递的参数值储存起来,程序的参数PSWORD指向它的位置。
程序检查PSWORD的内容与程序中存储的(’HELLO’)是否匹配。
在这里,两个值是一样的,所以程序继续运行。
*===============================================================*
*程序名:
EMPRPT2*
*有关文件:
EMPMST(物理文件)*
*PRINT(打印文件)*
*说明:
这个程序在输入的口令正确时,打印存储在EMPMST*
*文件中的雇员信息。
*
*在命令行进入“CALL库名/EMPRPT2(PSWORD)”,*
*这里PSWORD是这个程序的口令,口令是‘HELLO’。
*
*===============================================================*
FPRINTOF80PRINTER
FEMPMSTIPEKDISK
IEMPREC01
*-----------------------------------------------------------------*
*参数列表项是在这个程序中规定,有一个5个字符长的参数PSWORD。
*
*-----------------------------------------------------------------*
C*ENTRYPLIST
CPARMPSWORD5
*-----------------------------------------------------------------*
*检查字段PSWORD中的内容是否为’HELLO’。
如果不是,LR和*IN99为ON。
*
**IN99控制打印信息。
*
*-----------------------------------------------------------------*
CPSWORDIFNE'HELLO'
CSETONLR99
CENDIF
OPRINTH1P26
O50'EMPLOYEEINFORMATION'
OH1P
O12'NAME'
O34'SERIAL#'
O45'DEPT'
O56'TYPE'
OD01N99
OENAME20
OENUM32
OEDEPT45
OETYPE55
OD99
O16'***'
O40'InvalidPasswordEntered'
O43'***'
图30ILERPG/400程序
A*****************************************************************
A*说明:
这是物理文件EMPMST的DDS,它有一个记录格式EMPREC。
*
A*包括公司中每个雇员的记录。
*
A*****************************************************************
A*
AREMPREC
AENUM50TEXT('EMPLOYEENUMBER')
AENAME20TEXT('EMPLOYEENAME')
AETYPE1TEXT('EMPLOYEETYPE')
AEDEPT30TEXT('EMPLOYEEDEPARTMENT')
AENHRS31TEXT('EMPLOYEENORMALWEEKHOURS')
AKENUM
图31.EMPRPT的DDS
2.5.2从一个菜单驱动的应用程序中运行程序
另一种运行ILE程序的方法是用菜单驱动的应用程序。
工作站用户从菜单中选择选项,该菜单依次调用指定的程序。
图32给出了一个应用程序菜单的例子。
**
*PAYROLLDEPARTMENTMENU*
**
*Selectoneofthefollowing:
*
**
*1.Inquireintoemployeemaster*
*2.Changeemployeemaster*
*3.Addnewemployee*
**
**
**
**
**
**
**
**
**
**
**
*Selectionorcommand*
*===>*
**
*F3=ExitF4=PromptF9=RetrieveF12=Cancel*
*F13=InformationAssistantF16=AS/400mainmenu*
**
**
图32.应用程序菜单的例子
图32中的菜单上每个选项调用一个独立的ILE程序。
可以通过STRSDA命令,然后选择选项2(’设计菜单’)来建立一个菜单。
图33给出了上面PAYROLLDEPARTMEMTMENE显示文件的DDS。
源成员叫做PAYROL,类型为MNUDDS。
这个文件是使用SDA建立的。
A*FreeFormMenu:
PAYROL
A*
ADSPSIZ(2480*DS3-
A27132*DS4)
ACHGINPDFT
AINDARA
APRINT(*LIBL/QSYSPRT)
ARPAYROL
ADSPMOD(*DS3)
ALOCK
ASLNO(01)
ACLRL(*ALL)
AALWROL
ACF03
AHELP
AHOME
AHLPRTN
A134'PAYROLLDEPARTMENTMENU'
ADSPATR(HI)
A32'Selectoneofthefollowing:
'
ACOLOR(BLU)
A57'1.'
A67'2.'
A77'3.'
A*CMDPROMPTDonotdeletethisDDSspec.
A0192'Selectionorcommand-
A'
A511'Inquire'
A519'into'
A524'employee'
A533'master'
A611'Change'
A618'employee'
A627'master'
A711'Add'
A715'new'
A719'employee'
图33.应用程序菜单的数据描述
图34显示了在图32中给出的菜单程序的源语句。
源成员叫做PAYROLQQ,类型为MNUCMD。
它也是用SDA建立的。
PAYROLQQ,1
0001callRPGINQ
0002callRPGCHG
0003callRPGADD
图34.菜单程序的源语句
可以键入以下命令来运行该菜单:
GO库名/PAYROL
如果用户在菜单中输入1,2或3,那么图34中的程序就相应地调用RPGINQ,RPGCHG或RPGADD。
2.5.3使用用户建立的命令运行程序
可以使用命令定义建立一个命令,用此命令运行程序。
命令定义是一个目标(类型为*CMD),该目标包括命令的定义(包括命令名,参数描述,和有效性检查等信息),并指出执行命令功能要用的程序。
例如可以建立命令PAY,该命令调用程序PAYROL,程序PAYROL是要运行的程序名,可以交互地或在批处理作业中使用该命令。
并于使用命令定义的详细资料参见CL程序设计。
2.5.4回答运行时的询问信息
当运行有ILERPG/400过程的程序时,可能会产生运行时询问信息,没有处理异常的错误指示器或错误子例程时(*PSSR或INFSR),就会出现这些信息。
需要对询问信息作出应答程序才能继续运行下去。
可以把询问信息加到系统应答列表里从而自动地对这些信息作出应答。
这种应答询问信息的方法比较适合于批处理程序,否则就需操作员来作出回答。
可以把以下的ILERPG/400询问信息加到系统应答列表中。
注意:
ILERPG/400的询问信息,编码以RNQ为前缀。
要把询问信息添加到回答列表中应使用添加应答列表入口命令,键入:
ADDRPYLE顺序号信息编码
顺序号从1到9999,反映了加到列表中入口的位置,信息编码是要添加的信息号码。
对每条要添加的信息,重复这条命令。
使用修改作业(CHGJOB)命令(或其它CL作业命令)来显示作业对询问信息回答列表的使用。
这样,应把询问信息回答(INQMSGRPY)属性指定为*SYSRPYL。
只用于由作业送出的询问信息,此作业的INQMSGRPY指定为*SYSRPYL。
以下的CL命令中有INQMSGRPY参数。
修改作业(CHGJOB)
修改作业描述(CHGJOBD)
建立作业描述(CRTJOBD)
提交作业(SBMJOB)
也可以使用处理回答列表入口(WRKRPYLE)命令来修改或删除系统回答列表中的入口。
关于ADDRPYLE和WRKRPYLE命令的详细资料参考CL参考手册。
2.5.5结束ILE程序
当ILE程序正常结束,系统把控制返回给调用者。
调用者可以是工作站用户或其它程序(例如菜单处理程序)。
如果ILE程序异常结束,并且该程序与它的调用者运行在不同的活动组中,那么就会产生逃逸信息CEE9901,发出以下信息:
Errormessage-idCausedprogramtoend。
即错误信息使程序结束,并把控制返回给调用者。
使用监控信息命令(MONMSG)的CL程序可以监视这种异常。
也可以用其它ILE语言程序来监视异常。
如果ILE程序与其调用者在同一活动组中运行而异常结束,那么是否产生信息取决于程序结束的原因。
如果以功能检测结束,那么送出CPF9999。
如果由RPG过程产生异常,那么会产生以RNX为前缀的信息。
关于异常信息的详细资料,参见3.2.1节中的“异常情况处理概述”。
2.5.6管理活动组
活动组是作业的子结构,它由分配来运行一个或多个ILE或OPM程序的系统资源组成(例如,存储空间,落实定义,及打开文件)。
活动组可以使几个ILE程序在同一个作业中运行而彼此互不影响(例如,落实控制及复盖)。
它的基本思想是在同一活动组内活动的所有程序组成一个协作的应用程序。
应该在程序建立时指定它在哪个活动中运行。
活动组是在程序目标建立时由参数ACTGRP的指定值决定的。
(OPM程序总是在默认活动组中运行的。
不可以修改他们的活动组)。
一旦ILE程序(目标类型*PGM)被激活,他们就一直保持活动状态直到活动组被删除。
本单元的其余部分会告诉你如何指定一个活动组及怎样删除它。
关于活动组的详细资料参见ILE概念。
2.5.6.1指定活动组
要控制ILE程序在哪个活动组中运行是在建立程序(使用CRTPGM或CRTBNDRPG)或服务程序(使用CRTSRVPGM)时可以通过指定ACTGRP参数的值来实现的。
注意:
如果使用CRTBNDRPG命令,而DFTACTGRP值为*NO时,那么只能为ACTGRP指定一个值。
可以选择以下的值:
命名的活动组
命名的活动组允许把ILE程序和服务程序做为一个应用程序来管理。
当调用第一个在建立时指定了活动组名字的程序时活动组建立。
然后它被所有指定了相同活动组名的程序和服务程序使用。
当使用CL命令RCLACTGRP删除命名的活动组时该活动组结束。
这条命令只有当活动组不再使用后才能使用。
当它结束时,所有与活动组中的程序和服务程序相关联的资源返回给系统。
在CRTBNDRPG命令中,命名的活动组QILE是ACTGRP参数的默认值。
但是,因为活动组要对很多作业响应,所以建议为这个参数指定不同的值。
例如,你也许希望在应用程序命名后为活动组命名。
*NEW
当指定*NEW时,只要程序被调用就建立新的活动组。
系统为该活动组建立一个名字,在你的作业中,该名字是唯一的。
由*NEW建立的活动组在与之相关联的程序结束时结束。
因此,如果以LR为OFF来保持程序的活动状态而从程序中返回,那么就不能指定ACTGRP参数为*NEW。
注意:
对于服务程序这个值是无效的。
服务程序只能在命名的活动组或调用者的活动组中运行。
对于CRTPGM命令的ACTGRP参数*NEW是其默认值。
如果使用ACTGRP(*NEW)建立ILERPG/400程序,那么就可任意多次地调用该程序而不必从较早的调用中返回。
对每一次调用都会有该程序新的拷贝。
每个新的拷贝会有它自已的数据,打开它自已的文件,等等。
但是,必须保证有使其调用自身结束的办法。
否则,就会不断的建立新的活动组并且该程序将永远不会返回。
*CALLER
程序或服务程序将在调用程序所在的活动组中被激活。
如果以ACTGRP(*CALLER)建立的ILE程序被OPM程序所调用,那么它将在OPM默认活动组(*DFTACTGRP)中被激活。
2.5.6.2在OPM默认活动组中运行
当OS/400作业启动时,系统建立一个供OPM程序使用的活动组。
活动组的符号为*DFTACTGRP。
不能删除OPM默认活动组。
只在作业结束时由系统删除。
OPM程序自动地在OPM默认活动组中运行。
当出现以下情况时ILE程序也可以在OPM默认活动组中运行:
程序以CRTBNDRPG命令且DFTACTGRP(*YES)建立。
程序以ACTGRP(*CALLER)建立,并且调用程序是在默认活动组中运行。
注意对于CRTBNDRPG命令如果指定了DFTACTGRP(*NO),那么只能指定ACTGRP(*CALLER)。
注意:
由*CALLER决定在默认活动组中运行的程序,它所使用的资源直到作业结后才会被删除。
2.5.6.3维护OPMRPG/400和ILERPG/400程序的兼容性
如果你有由几个RPG程序组成的OPM应用程序,并且用下面的方法建立ILE应用程序,那么就可以确保转换后的应用程序象OPM应用程序那样工作:
1、使用CVTRPGSRC命令转换每个OPM源成员,注意要转换/COPY成员。
有关的详细资料,参见附录1.2.2节中的“转换你的源程序”。
2、使用CRTBNDRPG命令,独立地编译和连接每个转换过的源成员成为程序目标,指定DFTACTGRP(*YES)。
关于OPM兼容程序的详细资料,参见1.3.1节中的“策略1:
OPM兼容应用程序”。
2.5.6.4删除活动组
当活动组被删除时,它的资源就被收回了。
资源包括静态,存储空间及打开文件。
当与一个*NEW活动组相关联的程序返回到调用者时,该活动组被删除。
命名活动组(例如ILE)是稳定的活动组。
因为只有明确地删除或作业结束时,它们才被删除。
与运行在命名活动组中程序相关联的存储空间,要到活动组被删除时才被释放。
OPM默认活动组也是稳定活动组。
在默认活动组中运行的ILE程序相关联的存储空间在signoff(对于交互作业)或作业结束(对于批处理作业)时被释放。
如果有许多ILERPG/400程序处于活动状况(即至少调用了一次),那么系统的存储空间可能被占满。
因此,你应当避免让占用大量静态存储域的ILE程序在OPM默认的活动组中运行。
因为只有当作业结束时,这些存储空间才会被收回。
注意:
以DFTACTGRP(*YES)建立的ILERPG/400程序在它结束时,它的存储空间会被释放。
与服务程序相联系的存储空间只有当与之相关联的活动组结束时才会被收回。
如果服务程序被调用而在默认活动组中运行,那么在作业结束时,它的资源被收回。
可以使用RCLACTGRP命令删除命名活动组。
使用这个命令来删除那些不用的非默认活动组。
该命令提供了删除所有符合条件的活动组或按名字删除一个活动组的选项。
关于RCLACTGRP的详细资料参见CL参考手册。
关于RCLACTGRP与活动组的详细资料,参考ILE概念。
2.5.6.5回收资源命令
回收资源(RCLRSC)命令用来回收不再活动的程序所用的资源。
该命令根据程序建立方式的不同而有不同的工作方式。
如果程序是OPM程序或是以DFTACTGRP(*YES)建立的,那么RCLRSC命令将关闭打开的文件并释放静态存储空间。
对于以*CALLER建立在OPM默认活动组中被激活的ILE程序,当发出RCLRSC命令时文件被关闭,并且存储空间重新初始化。
但不释放存储空间。
对于与命名的活动组相关联的ILE程序,RCLRSC命令不起作用。
必须使用RCLACTGRP命令来释放命名活动组中的资源。
关于RCLRSC命令的详细资料,参见CL参考手册。
关于RCLRSC与活动组的详细资料,参见ILE概念。
2.5.7管理动态分配的存储空间
ILE允许你在程序中通过堆管理而直接管理运行时的存储空间。
堆是用于动态存储分配的存储区域。
应用程序所要求的动态存储空间数量取决于使用堆的程序和过程所处理的数据。
可以通过使用ILE可连接的AP1来管理堆。
不须明确地管理运行时存储空间。
但是,你可能希望使用动态分配的运行时存储空间。
例如,如果不知道确切的数组或多次出现的数据结构有多大,可能就希望这样。
可以定义数组或数据结构为BASED,并且当程序确定了它们的大小时,为它申请实际的存储空间。
在系统中有两种有效的堆:
默认的和用户建立的。
本单元的其余部分解释了如何使用默认的堆来管理ILERPG/400程序中的运行时存储空间。
关于用户建立的堆和其它ILE存储空间管理概念的详细介绍,参见ILE概念。
2.5.7.1管理默认的堆式空间
在一个活动组中对动态存储空间的首次请求导致了默认堆的建立,在这个堆里分配给它存储空间。
其后的动态空间请求都从这个堆中分配。
如果堆中的存储空间不能满足当前对动态存储的申请,那么堆空间被扩展,分配更多的存储空间。
已分配的存储空间直到明确地指出释放或直到堆被丢弃才会被释放。
当拥有默认堆的活动组结时,该堆才会被丢弃。
在同一活动组中的程序都使用同一个默认的堆。
如果一个程序存取的空间超出为它分配的存储空间,那么就会对其它程序产生问题。
例如,假定有两个程序,程序A和程序B在同一个活动组中运行。
有10个字节分配给程序A,但是程序A修改了11个字节。
如果多出的字节实际是分配给B的,那么程序B就会发生问题。
可以在一个活动组中分隔程序和过程的动态空间。
即建立一个或多个用户建立的堆。
关于建立这种用户建立的堆的资料,参见ILE概念。
对于默认堆可以使用以下的ILE可连接的AP1:
释放存储空间(CEEFRST)可连接的API释放一个以前分配的堆存储空间。
取得堆存储空间(CEEGTST)可连接的API在一个堆中分配存储空间。
重分配存储空间(CEECZST)可连接的API修改以前分配的存储空间的大小。
注意:
不能在用DFTACTGRP(*YES)建立的程序中使用以上或任何其它的ILE可连接的API。
这是因为在这种程序中不允许使用静态连接(通过CALLB操作)。
关于存储空间管理可连接的API的其他资料参见系统API参考手册。
2.5.7.1.1为一个运行时数组动态分配存储空间
下面的例子显示了怎样从一个ILERPG/400过程中管理属于默认堆的动态存储空间。
在这个例子中,过程DYNARRAY为一个实用非连接的压缩型数组动态地分配存储空间。
该过程的调用者可以从DYNARRAY中申请以下之一:
把一个元素添加到数组中
由数组中返回一个元素
释放数组的存储空间
DYNARRAY使用三个ILE可以连接存储空间的API:
CEEGTST(获取存储空间),CEECZST(重分配存储空间)和CEEFRST(释放存储空间)来完成这些操作。
图35显示了DYNARRAY的定义规范表。
把过程定义为使用a(15,0)压缩十进制数组。
只要简单地把元素定义改为字符型字段,就可以很容易转换成处理字符型数组。
*=================================================================*
*DYNARRAY:
分配一个无边界的压缩型(15,0)运行时数组,这个*
*过程分配这个数组,返回一个数组值并重分配数组。
*
*===========================
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 第八章 运行程序 第八 运行 程序