IBM Mainframe Assembler程序在添加COBOL调用后显示CPU时间和运行时间的极大跳跃.为什么?可以做些什么来加快速度?

dst*_*her 5 assembly mainframe

读取非常大的文件的IBM Mainframe Assembler程序被修改为每个记录调用一次COBOL"存根"程序.COBOL调用是必不可少的,但程序本身的工作很少.自然预计CPU略有增加,但测试表明CPU使用率和运行时间都有很大的增长.为什么?可以做些什么来加快速度?

足以重现问题的示例源代码:

(1)汇编程序,调用IEFBR14 8192次:

SAMPLE CSECT
       LR    12,15
       USING SAMPLE,12
       LHI   9,8192
LOOP   CALL  IEFBR14
       BCT   9,LOOP
       SR    15,15
       SVC   3
       END
Run Code Online (Sandbox Code Playgroud)

Log显示非常低的资源消耗,在调用无效的程序时是合理的.

EXCP    CPU    SRB  CLOCK   SERV  PG 
  11    .00    .00    .00    603   0
Run Code Online (Sandbox Code Playgroud)

(2)现在编写一个简单的COBOL程序,除了GOBACK之外什么都不做:

识别部门.
PROGRAM-ID.COBOL.
程序部门.回去.

......并且在同一循环中也称它为8192次:

SAMPLE CSECT              
       LR    12,15        
       USING CALLCOB,12   
       LHI   9,8192       
LOOP   CALL  IEFBR14         
       CALL  COBOL        
       BCT   9,LOOP       
       SVC   3            
       END
Run Code Online (Sandbox Code Playgroud)

耀!现在资源消耗相形见绌:

 EXCP    CPU    SRB  CLOCK   SERV  PG 
65552    .16    .00    .19  3980K   0 
Run Code Online (Sandbox Code Playgroud)

dst*_*her 8

至少从1990年代开始,标准IBM COBOL,PL/I和Fortran都包含一个名为"语言环境"(LE)的内置功能,它提供了一套对所有人共同的标准运行时可调用服务.在运行时,此"环境"由初始化例程建立,旨在跨所有后续中间语言调用提供持久服务.但是当Assembler 支持 LE时,它不是自动内置的.因此,当Assembler调用"LE兼容"语言(如COBOL)时,每次调用都会调用这些初始化例程,从而大大减慢了进程.解决方案是让Assembler"驱动程序"程序建立LE运行时环境,因此它会在所有后续调用中持续存在,并且只发生一次.值得庆幸的是,通过向Assembler源添加一些简单语句可以轻松完成.虽然很少而且简单,但放置至关重要.以下是一些示例"shell"代码,可用作模板:

SHELL CEEENTRY AUTO=DSALEN 
* COBOL CALL can be anywhere after CEEENTRY and before CEETERM 
       CEETERM ,
* declare constants here: 
CONSTANT DC    CL8'CONSTANT'
PPA    CEEPPA  ,  (P)rogram (P)rolog (A)rea
       CEEDSA  ,  (D)ynamic (S)torage (A)rea
* declare variables here: 
VARIABLE DS    CL8
DSALEN EQU     *-CEEDSA
       CEECAA ,
       END
Run Code Online (Sandbox Code Playgroud)

还有其他与LE相关的汇编程序宏(参见下面的链接),但上面的内容都是简单,高效的COBOL调用所需的全部内容.

将基本语句添加到Sample程序以使其"符合LE"后,但保持相同的IEFBR14/COBOL CALL循环:

SAMPLE CEEENTRY AUTO=DSALEN                    
       LHI   9,8192                            
LOOP   CALL  IEFBR14                           
       CALL  COBOL                             
       BCT   9,LOOP                            
       CEETERM ,                               
PPA    CEEPPA  ,  (P)ROGRAM (P)ROLOG (A)REA    
       CEEDSA  ,  (D)YNAMIC (S)TORAGE (A)REA   
DSALEN EQU     *-CEEDSA                        
       CEECAA ,                                
       END                                     
Run Code Online (Sandbox Code Playgroud)

...现在资源消耗对于调用一个也没有做任何事情的额外程序来说也是合理的:

 EXCP    CPU    SRB  CLOCK   SERV  PG 
   23    .00    .00    .00   1814   0 
Run Code Online (Sandbox Code Playgroud)

z/OS语言环境编程指南...专业编程任务...汇编程序注意事项...汇编程序宏:

http://www.ibm.com/support/knowledgecenter/en/SSLTBW_2.2.0/com.ibm.zos.v2r2.ceea200/clcasm5.htm

  • 语言运行时(LE)确实是罪魁祸首,因为原始海报的方法导致它被加载和卸载数千次.切换到符合LE的汇编程序的一个简单替代方法是简单地用任何LE语言编写"存根",然后调用汇编程序.我经常使用一个空C程序,只有一个main()调用一个链接汇编程序,正是出于这个原因. (2认同)