CL比较验证范围不起作用

时间:2019-01-24 19:17:06

标签: assembly mainframe zos

我正在验证一些输入;输入数字应为1到255。然后尝试以下代码。 已定义输入;输入DC CL60'

clc   input,=c'255'   
bh    loop1
clc   input,=c'1'     
bl    loop1
J     loop2 
loop1

以上验证仅适用于3位数字(从100到255) 但是它不适用于两位数的数字。您能帮我一下吗:)

2 个答案:

答案 0 :(得分:3)

很大程度上取决于您对“输入”字段的灵活性。例如,如果您需要以相同的方式处理C'1',C'1',C'1',C'01',C'01'和C'001',那么您需要做一些额外的工作。

通常,您有两种选择。您可以将数据“规范化”为三个字符的字段(换句话说,就是我在C'001'上面提到的所有示例),也可以进行一些富有想象力的可变长度比较,以适应您的值的大小重新尝试比较。

如果您对CLC的工作方式有更深入的了解,这对您来说更有意义。如果查看程序的汇编程序列表,您将看到以十六进制编码的CLC的目标代码...它将类似于D5llsaaatbbb,其中:

  • “ D5”是操作码-CLC
  • “ ll”是您要进行比较的长度
  • “ s”是第一个操作数基址寄存器
  • “ aaa”是第一个操作数位移
  • “ t”是第二个操作数基址寄存器
  • “ bbb”是第二个操作数位移

因此,如果您的输入字段确实是DC CL60'',并且存储在距离寄存器10较100字节的位置,而字面量(= C'whatever')距离寄存器12较40字节,则会看到D53BA064C028。编写足够的汇编程序代码,您将像阅读英语一样读这些东西。 :)

正如其他海报中所指出的那样,汇编程序将长度默认为第一个操作数的长度,因此,马上就遇到了问题,因为您正在执行比较(clc输入,= C'1 ')使汇编程序生成60字节的比较,即使第二个操作数只有一个字节长。如果您想以这种方式进行操作,则需要将其编码为clc输入,= CL60'1 ...'。这就是为什么通常更方便地编写指令“向后”(如clc = C'1',input)或显式指定长度(如clc input(1),= C'1')以便您不要无意间超出了要比较的字段的末尾。

您遇到的下一个问题是使比较变量为可变长度。很多时候,您会想知道自己有多少位数,然后比较这几位数而不是字段的长度。例如,您可能会查看编码为“ 1”的数据,并决定跳过空格,而仅将字段检查为一个字节的值。对于这种事情,execute(EX)指令是您的朋友-它为您提供了进行变长比较的简便方法。

比方说,您确定用户输入了一个字节,因此需要一个字节的CLC。假设您想要的长度在寄存器中,代码将如下所示:

* Assume you have the length in R1
       BCTR R1,0         Don't forget lengths are 0-relative (00 = 1 byte, FF=256)
       EX   R1,MYCLC     Do the comparison using the length in R1
       J    *+10         Skip over the CLC instruction
MYCLC  CLC  INPUT(0),PATTERN       Executed instruction

EX指令使用第一个操作数来更新目标指令,然后执行它。在示例中,EX使用R1中的值来设置CLC中的长度,从而可以进行可变长度比较。注意长度为0-在这种情况下,目标代码为D500,用00对R1的低位进行EX或运算,以得到所需的长度。简单吧?

难题的最后一部分是对INPUT字段进行一些解析,假设它是一个自由格式的字段,可以包含空白之类的内容。通常需要在较长的字符串中查找初始非空白字段...在这里,翻译测试(TRT)是您的朋友。我不会给您带来任何细节,但是它为您提供了一条指令,该指令可以扫描字段以查找任何特定字符-例如,非空白或空白。一对TRT指令可以帮助您找到任何带分隔符的字符串的开始和结尾,类似于C中的strchr()(如果您是C程序员)。稍微减去就可以得到一些长度,并且您都可以按照上面说明的可变长度比较来完成所需的工作。

在编写更多汇编器时,您将找出使这些任务更容易的所有小技巧。例如,EBCDIC的“功能”是数字的十六进制编码位于比例尺的顶部:F0至F9。这意味着在许多简单的应用程序中,您不必真正处理“高于999”的情况,因为所有的字母和典型符号都低于C'0'...只需检查不小于通常,对于字符数据,0就足够了。

无论如何,这里的一些提示应该可以助您一臂之力,而且我相信通过进行更多的研究,您将可以轻松获得期望的结果。

答案 1 :(得分:1)

当汇编器生成用于比较的长度时,它基于第一个操作数。您没有在代码中显示此内容,但我认为它类似于

INPUT DS CL3

在这种情况下,指令CLC input,=c'1'正在将一个3字节字段与1个字符文字进行比较。因此,您正在将三个字节的区域与一个1字符值的三个字节的区域进行比较,因此后两个字节是不确定的。

如果要基于文字进行比较,则可以改为:

         clc   =c'255',input   
         bh    loop1
         clc   =c'1',input     
         bl    loop1
         J     loop2 
loop1

尽管有更好的方法。您可以将输入转换为压缩的十进制格式,然后进行数值比较。

例如,假设这是您的代码:

             PACK DecimalInput,Input  
             CP   DecimalInput,=P'255'  
             BH   TooHigh  
             CP   DecimalInput,=P'1'  
             BL   TooLow
JustRight    DS  0H


DecimalInput DS   PL3 
Input        DS   CL3  

当然,您需要验证它们是否为数字,否则最终将得到S0C7。