Press enter to see results or esc to cancel.

LongInt Comparison

This procedure generates code to compare two LongInt values. Again, for some special cases shorter code is generated.

    Procedure GenerateCodeForLongIntComparisons;

      Procedure GenerateShortCircuitLongIntComparisonJumps;
      Const OpCodes: Array [Calc_IsEqual..Calc_IsLowerOrEqual, Boolean] of Byte = (
        (JNE,   0),
        (  0, JNE),
        ( JL,  JG),
        ( JG,  JL),
        ( JL,  JG),
        ( JG,  JL));
      begin
        If OpCodes [Operation, True] <> 0 then
          GenerateCodeForNearJump (LongIntComparisonLastJumpToTrue, OpCodes [Operation, True]);
        If OpCodes [Operation, False] <> 0 then
          GenerateCodeForNearJump (LongIntComparisonLastJumpToFalse, OpCodes [Operation, False]);
      end;

      Procedure GeneralGenerateCodeForLongIntComparisons;
      begin
        LoadBothExpressionsToRegisters (LeftExpression, RightExpression, [urDX, urAX]);
        RightExpression.SwitchBetweenLoWordAndHiWord (2);
        RightExpression.GenerateArithmeticInstructionWith_DX (mod_CMP_rm);
        GenerateShortCircuitLongIntComparisonJumps;
        RightExpression.SwitchBetweenLoWordAndHiWord (- 2);
        RightExpression.GenerateArithmeticInstructionWith_ACC (mod_CMP_rm);
      end;

      Procedure GenerateCodeForLongIntComparisonsWithConstant;
      begin
        If LeftExpression.Location = elMemory then
          begin
            LeftExpression.Calculate;
            Inc (LeftExpression.Value.Word, 2);
            LeftExpression.GenerateArithmeticInstructionWithImmediateValue (
                                            RightExpression.Value.LongRec.WordH,
                                            mod_CMP_rm);
            GenerateShortCircuitLongIntComparisonJumps;
            Dec (LeftExpression.Value.Word, 2);
            LeftExpression.GenerateArithmeticInstructionWithImmediateValue (
                                            RightExpression.Value.LongRec.WordL,
                                            mod_CMP_rm);
          end else GeneralGenerateCodeForLongIntComparisons;
      end;

    begin
      LongIntComparisonLastJumpToTrue := 0;
      LongIntComparisonLastJumpToFalse := 0;
      If RightExpression.Location = elConstant then
        begin
          If RightExpression.Value.LongRec.Long <> 0 then GenerateCodeForLongIntComparisonsWithConstant
            else begin
                   Case Operation of
                     Calc_IsEqual,
                     Calc_IsNotEqual: Case LeftExpression.Location of
                                        elMemory:
                                          begin
                                            LeftExpression.Calculate;
                                            Exclude (LeftExpression.DataType, it32Bit);
                                            LeftExpression.LoadExpressionToRegister (rAX);
                                            Inc (LeftExpression.Value.Word, 2);
                                            LeftExpression.GenerateArithmeticInstructionWith_ACC (mod_OR_rm);
                                            Include (LeftExpression.UsedRegisters, urAX);
                                          end;
                                        else begin
                                               LeftExpression.Calculate;
                                               GenerateInstruction_Word (OR_AX_DX);
                                             end;
                                      end;
                     else GenerateCodeForLongIntComparisonsWithConstant;
                   end;
                 end;
        end else GeneralGenerateCodeForLongIntComparisons;
      LeftExpression.SetExpressionToBooleanJump (UnsignedConditionalJumpOpCode [Operation]);
      With LeftExpression do
        begin
          Value.LastJumpToTrue  := LongIntComparisonLastJumpToTrue;
          Value.LastJumpToFalse := LongIntComparisonLastJumpToFalse;
        end;
    end;