Previous: Machine-Independent Predicates, Up: Predicates


16.7.2 定义机器特定的predicate

许多机器对操作数的要求无法使用通用的predicate来精确表达。 你可以使用表达式define_predicatedefine_special_predicate来定义 额外的predicate。这些表达式具有三个操作数:

程序genrecog扫描define_predicatedefine_special_predicate表达式来决定什么RTX代码可能被允许。 你应该使其在RTL predicate表达式中总是显式的, 使用MATCH_OPERANDMATCH_CODE

这里有一个简单的定义predicate的例子,来自IA64机器描述:

     ;; True if op is a SYMBOL_REF which refers to the sdata section.
     (define_predicate "small_addr_symbolic_operand"
       (and (match_code "symbol_ref")
            (match_test "SYMBOL_REF_SMALL_ADDR_P (op)")))

另一个例子,展示了C块的使用。

     ;; True if op is a register operand that is (or could be) a GR reg.
     (define_predicate "gr_register_operand"
       (match_operand 0 "register_operand")
     {
       unsigned int regno;
       if (GET_CODE (op) == SUBREG)
         op = SUBREG_REG (op);
     
       regno = REGNO (op);
       return (regno >= FIRST_PSEUDO_REGISTER || GENERAL_REGNO_P (regno));
     })

使用define_predicate编写的predicate会自动包含一个测试, 用来测试modeVOIDmode, 或者op具有与mode相同的机器模式, 或者opCONST_INTCONST_DOUBLE。 它们专门检查整数CONST_DOUBLE, 也不测试每种常量的值是否适合所需求的机器模式。 这是因为接受常量的目标机特定的predicate,通常必须做更严厉的值检查。 如果你需要确切的通用predicate提供的对CONST_INTCONST_DOUBLE的对待, 则可以使用MATCH_OPERAND子表达式来调用const_int_operand, const_double_operand或者immediate_operand

使用define_special_predicate编写的predicate不做任何自动的机器模式检查, 并且genrecog将其作为具有特定的机器模式处理来对待。

程序genpreds负责生成代码来测试predicate。 其还编写了一个包含所有机器特定predicate的函数声明的头文件。 所以不需要在cpu-protos.h中声明这些predicate。