В противном случае просто используйте скалярный код, начиная с самого значимого фрагмента, для проверки диапазона.
На процессоре, который использует cmp
и регистр флагов, это делается следующим образом:
- Сравните старшие части (например, старшие 32 бита) чисел (
cmp
инструкция)
- Если не равно «Равно», перейдите к «EndOfCompare» (x86:
jne
инструкция)
- Сравните следующие части (например, 32 бита) чисел
- Если не равно «Равно», перейдите к «EndOfCompare»
- ...
- Сравните следующие части (например, 32 бита) чисел
- Если не равно «Равно», перейдите к «EndOfCompare»
- Сравните младшие части (например, младшие 32 бита) чисел
- "EndOfCompare":
В этот момент регистр флагов содержит информацию о порядке (a<b
, a=b
или a>b
) двух больших чисел, точно так же, как вы делали простую инструкцию cmp
, сравнивающую два маленьких числа.
К сожалению, этот простой вариант будет работать только с числами без знака.
Кстати, обычно блок "выровнен" в пространстве IP-адресов, поэтому вам нужно только проверить маску младших битов и сравнить старшие биты на равенство.
Проверка для (A AND MASK) = (B AND MASK)
может выполняться следующим образом на 32-разрядном процессоре:
mov ecx, part 1 of A
xor ecx, part 1 of B
and ecx, part 1 of MASK
mov eax, part 2 of A
xor eax, part 2 of B
and eax, part 2 of MASK
or ecx, eax
mov eax, part 3 of A
xor eax, part 3 of B
and eax, part 3 of MASK
or ecx, eax
...
В случае 128-битного числа вам нужно 4 "части".
Не имеет значения, является ли "часть 1" старшим или младшим битом чисел.
Если (A AND MASK) = (B AND MASK)
имеет значение true, ecx
будет иметь значение 0 (и флаг нуля будет установлен из-за инструкции or
).