This commit is contained in:
darealshinji 2026-08-16 19:17:25 +02:00 committed by GitHub
commit cbf3ffdeea
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
14 changed files with 2562 additions and 2757 deletions

View file

@ -1,341 +0,0 @@
; 7zAsm.asm -- ASM macros
; 2023-12-08 : Igor Pavlov : Public domain
; UASM can require these changes
; OPTION FRAMEPRESERVEFLAGS:ON
; OPTION PROLOGUE:NONE
; OPTION EPILOGUE:NONE
ifdef @wordsize
; @wordsize is defined only in JWASM and ASMC and is not defined in MASM
; @wordsize eq 8 for 64-bit x64
; @wordsize eq 2 for 32-bit x86
if @wordsize eq 8
x64 equ 1
endif
else
ifdef RAX
x64 equ 1
endif
endif
ifdef x64
IS_X64 equ 1
else
IS_X64 equ 0
endif
ifdef ABI_LINUX
IS_LINUX equ 1
else
IS_LINUX equ 0
endif
ifndef x64
; Use ABI_CDECL for x86 (32-bit) only
; if ABI_CDECL is not defined, we use fastcall abi
ifdef ABI_CDECL
IS_CDECL equ 1
else
IS_CDECL equ 0
endif
endif
OPTION PROLOGUE:NONE
OPTION EPILOGUE:NONE
MY_ASM_START macro
ifdef x64
.code
else
.386
.model flat
_TEXT$00 SEGMENT PARA PUBLIC 'CODE'
endif
endm
MY_PROC macro name:req, numParams:req
align 16
proc_numParams = numParams
if (IS_X64 gt 0)
proc_name equ name
elseif (IS_LINUX gt 0)
proc_name equ name
elseif (IS_CDECL gt 0)
proc_name equ @CatStr(_,name)
else
proc_name equ @CatStr(@,name,@, %numParams * 4)
endif
proc_name PROC
endm
MY_ENDP macro
if (IS_X64 gt 0)
ret
elseif (IS_CDECL gt 0)
ret
elseif (proc_numParams LT 3)
ret
else
ret (proc_numParams - 2) * 4
endif
proc_name ENDP
endm
ifdef x64
REG_SIZE equ 8
REG_LOGAR_SIZE equ 3
else
REG_SIZE equ 4
REG_LOGAR_SIZE equ 2
endif
x0 equ EAX
x1 equ ECX
x2 equ EDX
x3 equ EBX
x4 equ ESP
x5 equ EBP
x6 equ ESI
x7 equ EDI
x0_W equ AX
x1_W equ CX
x2_W equ DX
x3_W equ BX
x5_W equ BP
x6_W equ SI
x7_W equ DI
x0_L equ AL
x1_L equ CL
x2_L equ DL
x3_L equ BL
x0_H equ AH
x1_H equ CH
x2_H equ DH
x3_H equ BH
; r0_L equ AL
; r1_L equ CL
; r2_L equ DL
; r3_L equ BL
; r0_H equ AH
; r1_H equ CH
; r2_H equ DH
; r3_H equ BH
ifdef x64
x5_L equ BPL
x6_L equ SIL
x7_L equ DIL
x8_L equ r8b
x9_L equ r9b
x10_L equ r10b
x11_L equ r11b
x12_L equ r12b
x13_L equ r13b
x14_L equ r14b
x15_L equ r15b
r0 equ RAX
r1 equ RCX
r2 equ RDX
r3 equ RBX
r4 equ RSP
r5 equ RBP
r6 equ RSI
r7 equ RDI
x8 equ r8d
x9 equ r9d
x10 equ r10d
x11 equ r11d
x12 equ r12d
x13 equ r13d
x14 equ r14d
x15 equ r15d
else
r0 equ x0
r1 equ x1
r2 equ x2
r3 equ x3
r4 equ x4
r5 equ x5
r6 equ x6
r7 equ x7
endif
x0_R equ r0
x1_R equ r1
x2_R equ r2
x3_R equ r3
x4_R equ r4
x5_R equ r5
x6_R equ r6
x7_R equ r7
x8_R equ r8
x9_R equ r9
x10_R equ r10
x11_R equ r11
x12_R equ r12
x13_R equ r13
x14_R equ r14
x15_R equ r15
ifdef x64
ifdef ABI_LINUX
MY_PUSH_2_REGS macro
push r3
push r5
endm
MY_POP_2_REGS macro
pop r5
pop r3
endm
endif
endif
MY_PUSH_4_REGS macro
push r3
push r5
push r6
push r7
endm
MY_POP_4_REGS macro
pop r7
pop r6
pop r5
pop r3
endm
; for fastcall and for WIN-x64
REG_PARAM_0_x equ x1
REG_PARAM_0 equ r1
REG_PARAM_1_x equ x2
REG_PARAM_1 equ r2
ifndef x64
; for x86-fastcall
REG_ABI_PARAM_0_x equ REG_PARAM_0_x
REG_ABI_PARAM_0 equ REG_PARAM_0
REG_ABI_PARAM_1_x equ REG_PARAM_1_x
REG_ABI_PARAM_1 equ REG_PARAM_1
MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 macro
MY_PUSH_4_REGS
endm
MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 macro
MY_POP_4_REGS
endm
else
; x64
if (IS_LINUX eq 0)
; for WIN-x64:
REG_PARAM_2_x equ x8
REG_PARAM_2 equ r8
REG_PARAM_3 equ r9
REG_ABI_PARAM_0_x equ REG_PARAM_0_x
REG_ABI_PARAM_0 equ REG_PARAM_0
REG_ABI_PARAM_1_x equ REG_PARAM_1_x
REG_ABI_PARAM_1 equ REG_PARAM_1
REG_ABI_PARAM_2_x equ REG_PARAM_2_x
REG_ABI_PARAM_2 equ REG_PARAM_2
REG_ABI_PARAM_3 equ REG_PARAM_3
else
; for LINUX-x64:
REG_LINUX_PARAM_0_x equ x7
REG_LINUX_PARAM_0 equ r7
REG_LINUX_PARAM_1_x equ x6
REG_LINUX_PARAM_1 equ r6
REG_LINUX_PARAM_2 equ r2
REG_LINUX_PARAM_3 equ r1
REG_LINUX_PARAM_4_x equ x8
REG_LINUX_PARAM_4 equ r8
REG_LINUX_PARAM_5 equ r9
REG_ABI_PARAM_0_x equ REG_LINUX_PARAM_0_x
REG_ABI_PARAM_0 equ REG_LINUX_PARAM_0
REG_ABI_PARAM_1_x equ REG_LINUX_PARAM_1_x
REG_ABI_PARAM_1 equ REG_LINUX_PARAM_1
REG_ABI_PARAM_2 equ REG_LINUX_PARAM_2
REG_ABI_PARAM_3 equ REG_LINUX_PARAM_3
REG_ABI_PARAM_4_x equ REG_LINUX_PARAM_4_x
REG_ABI_PARAM_4 equ REG_LINUX_PARAM_4
REG_ABI_PARAM_5 equ REG_LINUX_PARAM_5
MY_ABI_LINUX_TO_WIN_2 macro
mov r2, r6
mov r1, r7
endm
MY_ABI_LINUX_TO_WIN_3 macro
mov r8, r2
mov r2, r6
mov r1, r7
endm
MY_ABI_LINUX_TO_WIN_4 macro
mov r9, r1
mov r8, r2
mov r2, r6
mov r1, r7
endm
endif ; IS_LINUX
MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 macro
if (IS_LINUX gt 0)
MY_PUSH_2_REGS
else
MY_PUSH_4_REGS
endif
endm
MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 macro
if (IS_LINUX gt 0)
MY_POP_2_REGS
else
MY_POP_4_REGS
endif
endm
MY_PUSH_PRESERVED_ABI_REGS macro
MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
push r12
push r13
push r14
push r15
endm
MY_POP_PRESERVED_ABI_REGS macro
pop r15
pop r14
pop r13
pop r12
MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
endm
endif ; x64

377
Asm/x86/7zAsm.inc Normal file
View file

@ -0,0 +1,377 @@
; 7zAsm.asm -- ASM macros
; 2023-12-08 : Igor Pavlov : Public domain
; 2026-07-29 : Carsten Janssen : x86 ASM files were translated from MASM into NASM dialect
%define XBITS __?BITS?__
%define WINDOWS 1
%define LINUX 2
%ifidni __?OUTPUT_FORMAT?__, win32
%define ABI WINDOWS
%elifidni __?OUTPUT_FORMAT?__, win64
%define ABI WINDOWS
%else
%define ABI LINUX
%endif
; Use ABI_CDECL for x86 (32-bit) only
; if ABI_CDECL is not defined, we use fastcall ABI
%if (XBITS == 32) && (ABI == WINDOWS)
%ifdef ABI_CDECL
%define IS_CDECL 1
%endif
%endif
%ifndef IS_CDECL
%define IS_CDECL 0
%endif
%if IS_CDECL == 1
%pragma win gprefix _
%endif
%macro MY_ASM_START 0
default rel
%use smartalign
%if XBITS == 32
[section .text$00 align=16 exec]
%else
[section .text]
%endif
%endmacro
%if ABI == LINUX
%define READONLY .rodata
%else
%define READONLY .rdata
%endif
%macro GLOBAL_FUNC 1
%if ABI == LINUX
global %1: function
%else
global %1
%endif
%1:
%endmacro
%macro MY_PROC 2
ALIGN 16
%assign proc_numParams %2
%if (XBITS == 64) || (ABI == LINUX) || (IS_CDECL == 1)
GLOBAL_FUNC %1
%else
GLOBAL_FUNC %tok(%strcat(@, %1, @, %eval(%2 * 4)))
%endif
%endmacro
%macro MY_ENDP 0
%if (XBITS == 64) || (IS_CDECL == 1) || (proc_numParams < 3)
ret
%else
ret (proc_numParams - 2) * 4
%endif
%endmacro
%if XBITS == 64
%define REG_SIZE 8
%define REG_LOGAR_SIZE 3
%else
%define REG_SIZE 4
%define REG_LOGAR_SIZE 2
%endif
%define x0 EAX
%define x1 ECX
%define x2 EDX
%define x3 EBX
%define x4 ESP
%define x5 EBP
%define x6 ESI
%define x7 EDI
%define x0_W AX
%define x1_W CX
%define x2_W DX
%define x3_W BX
%define x5_W BP
%define x6_W SI
%define x7_W DI
%define x0_L AL
%define x1_L CL
%define x2_L DL
%define x3_L BL
%define x0_H AH
%define x1_H CH
%define x2_H DH
%define x3_H BH
; %define r0_L AL
; %define r1_L CL
; %define r2_L DL
; %define r3_L BL
; %define r0_H AH
; %define r1_H CH
; %define r2_H DH
; %define r3_H BH
%if XBITS == 64
%define x5_L BPL
%define x6_L SIL
%define x7_L DIL
%define x8_L r8b
%define x9_L r9b
%define x10_L r10b
%define x11_L r11b
%define x12_L r12b
%define x13_L r13b
%define x14_L r14b
%define x15_L r15b
%define r0 RAX
%define r1 RCX
%define r2 RDX
%define r3 RBX
%define r4 RSP
%define r5 RBP
%define r6 RSI
%define r7 RDI
%define x8 r8d
%define x9 r9d
%define x10 r10d
%define x11 r11d
%define x12 r12d
%define x13 r13d
%define x14 r14d
%define x15 r15d
%else
%define r0 x0
%define r1 x1
%define r2 x2
%define r3 x3
%define r4 x4
%define r5 x5
%define r6 x6
%define r7 x7
%endif
%define x0_R r0
%define x1_R r1
%define x2_R r2
%define x3_R r3
%define x4_R r4
%define x5_R r5
%define x6_R r6
%define x7_R r7
%define x8_R r8
%define x9_R r9
%define x10_R r10
%define x11_R r11
%define x12_R r12
%define x13_R r13
%define x14_R r14
%define x15_R r15
%if (XBITS == 64) && (ABI == LINUX)
%macro MY_PUSH_2_REGS 0
push r3
push r5
%endmacro
%macro MY_POP_2_REGS 0
pop r5
pop r3
%endmacro
%endif
%macro MY_PUSH_4_REGS 0
push r3
push r5
push r6
push r7
%endmacro
%macro MY_POP_4_REGS 0
pop r7
pop r6
pop r5
pop r3
%endmacro
; for fastcall and for WIN-x64
%define REG_PARAM_0_x x1
%define REG_PARAM_0 r1
%define REG_PARAM_1_x x2
%define REG_PARAM_1 r2
%if XBITS == 32
; for x86-fastcall
%define REG_ABI_PARAM_0_x REG_PARAM_0_x
%define REG_ABI_PARAM_0 REG_PARAM_0
%define REG_ABI_PARAM_1_x REG_PARAM_1_x
%define REG_ABI_PARAM_1 REG_PARAM_1
%macro MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 0
MY_PUSH_4_REGS
%endmacro
%macro MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 0
MY_POP_4_REGS
%endmacro
%else
; x64
%if ABI == WINDOWS
; for WIN-x64:
%define REG_PARAM_2_x x8
%define REG_PARAM_2 r8
%define REG_PARAM_3 r9
%define REG_ABI_PARAM_0_x REG_PARAM_0_x
%define REG_ABI_PARAM_0 REG_PARAM_0
%define REG_ABI_PARAM_1_x REG_PARAM_1_x
%define REG_ABI_PARAM_1 REG_PARAM_1
%define REG_ABI_PARAM_2_x REG_PARAM_2_x
%define REG_ABI_PARAM_2 REG_PARAM_2
%define REG_ABI_PARAM_3 REG_PARAM_3
%else
; for LINUX-x64:
%define REG_LINUX_PARAM_0_x x7
%define REG_LINUX_PARAM_0 r7
%define REG_LINUX_PARAM_1_x x6
%define REG_LINUX_PARAM_1 r6
%define REG_LINUX_PARAM_2 r2
%define REG_LINUX_PARAM_3 r1
%define REG_LINUX_PARAM_4_x x8
%define REG_LINUX_PARAM_4 r8
%define REG_LINUX_PARAM_5 r9
%define REG_ABI_PARAM_0_x REG_LINUX_PARAM_0_x
%define REG_ABI_PARAM_0 REG_LINUX_PARAM_0
%define REG_ABI_PARAM_1_x REG_LINUX_PARAM_1_x
%define REG_ABI_PARAM_1 REG_LINUX_PARAM_1
%define REG_ABI_PARAM_2 REG_LINUX_PARAM_2
%define REG_ABI_PARAM_3 REG_LINUX_PARAM_3
%define REG_ABI_PARAM_4_x REG_LINUX_PARAM_4_x
%define REG_ABI_PARAM_4 REG_LINUX_PARAM_4
%define REG_ABI_PARAM_5 REG_LINUX_PARAM_5
%macro MY_ABI_LINUX_TO_WIN_2 0
mov r2, r6
mov r1, r7
%endmacro
%macro MY_ABI_LINUX_TO_WIN_3 0
mov r8, r2
mov r2, r6
mov r1, r7
%endmacro
%macro MY_ABI_LINUX_TO_WIN_4 0
mov r9, r1
mov r8, r2
mov r2, r6
mov r1, r7
%endmacro
%endif ; IS_LINUX
%macro MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 0
%if ABI == LINUX
MY_PUSH_2_REGS
%else
MY_PUSH_4_REGS
%endif
%endmacro
%macro MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11 0
%if ABI == LINUX
MY_POP_2_REGS
%else
MY_POP_4_REGS
%endif
%endmacro
%macro MY_PUSH_PRESERVED_ABI_REGS 0
MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
push r12
push r13
push r14
push r15
%endmacro
%macro MY_POP_PRESERVED_ABI_REGS 0
pop r15
pop r14
pop r13
pop r12
MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
%endmacro
%endif ; x64
%macro MOVZXLOHI 3 ; dest, src, suffix
%assign n %find(%2,x0,x1,x2,x3,x4,x5,x6,x7,x8,x9)
%if n == 0
%fatal <MOVZXLOHI_src_param_IS_INCORRECT>
%else
; x<n> ==> x<n>_L or x<n>_H
movzx %1, %tok(%strcat("x", %eval(n-1), %3))
%endif
%endmacro
%macro MOVZXLO 2 ; dest, src
MOVZXLOHI %1, %2, "_L"
%endmacro
%macro MOVZXHI 2 ; dest, src
MOVZXLOHI %1, %2, "_H"
%endmacro
%define mod %%
%define AddNum(x, n) %tok(%strcat(x, %eval(n)))
%define XMM_REG(n) AddNum(xmm, n)
%define YMM_REG(n) AddNum(ymm, n)
%macro XMMOP 3-4 ; op, reg1, reg2
%if %0 == 4
%1 XMM_REG(%2), XMM_REG(%3), %4
%else
%1 XMM_REG(%2), XMM_REG(%3)
%endif
%endmacro
%assign labelnum 0
%define anonlabel "..@mylabel_"
; automatically numbered label
%macro @@ 1
%ifnidn %1, :
%fatal <LABEL_WITHOUT_COLON>
%endif
AddNum(anonlabel, labelnum)%1
%assign labelnum labelnum+1
%endmacro
%define @F AddNum(anonlabel, labelnum) ; forward to next @@ label
%define @B AddNum(anonlabel, labelnum-1) ; back to previous @@ label

View file

@ -1,222 +1,220 @@
; 7zCrcOpt.asm -- CRC32 calculation : optimized version
; 2023-12-08 : Igor Pavlov : Public domain
include 7zAsm.asm
%include "7zAsm.inc"
MY_ASM_START
NUM_WORDS equ 3
UNROLL_CNT equ 2
%define NUM_WORDS 3
%define UNROLL_CNT 2
if (NUM_WORDS lt 1) or (NUM_WORDS gt 64)
.err <NUM_WORDS_IS_INCORRECT>
endif
if (UNROLL_CNT lt 1)
.err <UNROLL_CNT_IS_INCORRECT>
endif
%if (NUM_WORDS < 1) || (NUM_WORDS > 64)
%fatal <NUM_WORDS_IS_INCORRECT>
%endif
%if UNROLL_CNT < 1
%fatal <UNROLL_CNT_IS_INCORRECT>
%endif
rD equ r2
rD_x equ x2
rN equ r7
rT equ r5
%define rD r2
%define rD_x x2
%define rN r7
%define rT r5
ifndef x64
if (IS_CDECL gt 0)
crc_OFFS equ (REG_SIZE * 5)
data_OFFS equ (REG_SIZE + crc_OFFS)
size_OFFS equ (REG_SIZE + data_OFFS)
else
size_OFFS equ (REG_SIZE * 5)
endif
table_OFFS equ (REG_SIZE + size_OFFS)
endif
%if XBITS == 32
%if IS_CDECL == 1
%define crc_OFFS (REG_SIZE * 5)
%define data_OFFS (REG_SIZE + crc_OFFS)
%define size_OFFS (REG_SIZE + data_OFFS)
%else
%define size_OFFS (REG_SIZE * 5)
%endif
%define table_OFFS (REG_SIZE + size_OFFS)
%endif
; rN + rD is same speed as rD, but we reduce one instruction in loop
SRCDAT_1 equ rN + rD * 1 + 1 *
SRCDAT_4 equ rN + rD * 1 + 4 *
%define SRCDAT_1 rN + rD * 1 + 1 *
%define SRCDAT_4 rN + rD * 1 + 4 *
CRC macro op:req, dest:req, src:req, t:req
op dest, dword ptr [rT + @CatStr(src, _R) * 4 + 0400h * (t)]
endm
CRC_XOR macro dest:req, src:req, t:req
CRC xor, dest, src, t
endm
%macro CRC 4 ; op, dest, src, t
%assign n %find(%3, x0,x1,x2,x3,x4,x5,x6,x7,x8,x9)
%if n == 0
%fatal <CRC_src_param_IS_INCORRECT>
%else
; x<n> ==> r<n>
%1 %2, [rT + %tok(%strcat('r', %eval(n-1))) * 4 + 0400h * (%4)]
%endif
%endmacro
CRC_MOV macro dest:req, src:req, t:req
CRC mov, dest, src, t
endm
%macro CRC_XOR 3 ; dest, src, t
CRC xor, %1, %2, %3
%endmacro
MOVZXLO macro dest:req, src:req
movzx dest, @CatStr(src, _L)
endm
MOVZXHI macro dest:req, src:req
movzx dest, @CatStr(src, _H)
endm
%macro CRC_MOV 3 ; dest, src, t
CRC mov, %1, %2, %3
%endmacro
; movzx x0, x0_L - is slow in some cpus (ivb), if same register for src and dest
; movzx x3, x0_L sometimes is 0 cycles latency (not always)
; movzx x3, x0_L sometimes is 0.5 cycles latency
; movzx x3, x0_H is 2 cycles latency in some cpus
CRC1b macro
movzx x6, byte ptr [rD]
%macro CRC1b 0
movzx x6, byte [rD]
MOVZXLO x3, x0
inc rD
shr x0, 8
xor x6, x3
CRC_XOR x0, x6, 0
dec rN
endm
%endmacro
LOAD_1 macro dest:req, t:req, iter:req, index:req
movzx dest, byte ptr [SRCDAT_1 (4 * (NUM_WORDS - 1 - t + iter * NUM_WORDS) + index)]
endm
%macro LOAD_1 4 ; dest, t, iter, index
movzx %1, byte [SRCDAT_1 (4 * (NUM_WORDS - 1 - %2 + %3 * NUM_WORDS) + %4)]
%endmacro
LOAD_2 macro dest:req, t:req, iter:req, index:req
movzx dest, word ptr [SRCDAT_1 (4 * (NUM_WORDS - 1 - t + iter * NUM_WORDS) + index)]
endm
%macro LOAD_2 4 ; dest, t, iter, index
movzx %1, word [SRCDAT_1 (4 * (NUM_WORDS - 1 - %2 + %3 * NUM_WORDS) + %4)]
%endmacro
CRC_QUAD macro nn, t:req, iter:req
ifdef x64
%macro CRC_QUAD 3 ; nn, t, iter
%if XBITS == 64
; paired memory loads give 1-3% speed gain, but it uses more registers
LOAD_2 x3, t, iter, 0
LOAD_2 x9, t, iter, 2
LOAD_2 x3, %2, %3, 0
LOAD_2 x9, %2, %3, 2
MOVZXLO x6, x3
shr x3, 8
CRC_XOR nn, x6, t * 4 + 3
CRC_XOR %1, x6, %2 * 4 + 3
MOVZXLO x6, x9
shr x9, 8
CRC_XOR nn, x3, t * 4 + 2
CRC_XOR nn, x6, t * 4 + 1
CRC_XOR nn, x9, t * 4 + 0
elseif 0
LOAD_2 x3, t, iter, 0
CRC_XOR %1, x3, %2 * 4 + 2
CRC_XOR %1, x6, %2 * 4 + 1
CRC_XOR %1, x9, %2 * 4 + 0
%elif 0
LOAD_2 x3, %2, %3, 0
MOVZXLO x6, x3
shr x3, 8
CRC_XOR nn, x6, t * 4 + 3
CRC_XOR nn, x3, t * 4 + 2
LOAD_2 x3, t, iter, 2
CRC_XOR %1, x6, %2 * 4 + 3
CRC_XOR %1, x3, %2 * 4 + 2
LOAD_2 x3, %2, %3, 2
MOVZXLO x6, x3
shr x3, 8
CRC_XOR nn, x6, t * 4 + 1
CRC_XOR nn, x3, t * 4 + 0
elseif 0
LOAD_1 x3, t, iter, 0
LOAD_1 x6, t, iter, 1
CRC_XOR nn, x3, t * 4 + 3
CRC_XOR nn, x6, t * 4 + 2
LOAD_1 x3, t, iter, 2
LOAD_1 x6, t, iter, 3
CRC_XOR nn, x3, t * 4 + 1
CRC_XOR nn, x6, t * 4 + 0
else
CRC_XOR %1, x6, %2 * 4 + 1
CRC_XOR %1, x3, %2 * 4 + 0
%elif 0
LOAD_1 x3, %2, %3, 0
LOAD_1 x6, %2, %3, 1
CRC_XOR %1, x3, %2 * 4 + 3
CRC_XOR %1, x6, %2 * 4 + 2
LOAD_1 x3, %2, %3, 2
LOAD_1 x6, %2, %3, 3
CRC_XOR %1, x3, %2 * 4 + 1
CRC_XOR %1, x6, %2 * 4 + 0
%else
; 32-bit load is better if there is only one read port (core2)
; but that code can be slower if there are 2 read ports (snb)
mov x3, dword ptr [SRCDAT_1 (4 * (NUM_WORDS - 1 - t + iter * NUM_WORDS) + 0)]
mov x3, dword [SRCDAT_1 (4 * (NUM_WORDS - 1 - %2 + %3 * NUM_WORDS) + 0)]
MOVZXLO x6, x3
CRC_XOR nn, x6, t * 4 + 3
CRC_XOR %1, x6, %2 * 4 + 3
MOVZXHI x6, x3
shr x3, 16
CRC_XOR nn, x6, t * 4 + 2
CRC_XOR %1, x6, %2 * 4 + 2
MOVZXLO x6, x3
shr x3, 8
CRC_XOR nn, x6, t * 4 + 1
CRC_XOR nn, x3, t * 4 + 0
endif
endm
CRC_XOR %1, x6, %2 * 4 + 1
CRC_XOR %1, x3, %2 * 4 + 0
%endif
%endmacro
LAST equ (4 * (NUM_WORDS - 1))
%define LAST (4 * (NUM_WORDS - 1))
CRC_ITER macro qq, nn, iter
mov nn, [SRCDAT_4 (NUM_WORDS * (1 + iter))]
%macro CRC_ITER 3 ; qq, nn, iter
mov %2, [SRCDAT_4 (NUM_WORDS * (1 + %3))]
i = 0
rept NUM_WORDS - 1
CRC_QUAD nn, i, iter
i = i + 1
endm
%assign i 0
%rep NUM_WORDS - 1
CRC_QUAD %2, i, %3
%assign i i+1
%endrep
MOVZXLO x6, qq
mov x3, qq
MOVZXLO x6, %1
mov x3, %1
shr x3, 24
CRC_XOR nn, x6, LAST + 3
CRC_XOR nn, x3, LAST + 0
ror qq, 16
MOVZXLO x6, qq
shr qq, 24
CRC_XOR nn, x6, LAST + 1
if ((UNROLL_CNT and 1) eq 1) and (iter eq (UNROLL_CNT - 1))
CRC_MOV qq, qq, LAST + 2
xor qq, nn
else
CRC_XOR nn, qq, LAST + 2
endif
endm
CRC_XOR %2, x6, LAST + 3
CRC_XOR %2, x3, LAST + 0
ror %1, 16
MOVZXLO x6, %1
shr %1, 24
CRC_XOR %2, x6, LAST + 1
%if ((UNROLL_CNT & 1) == 1) && (%3 == (UNROLL_CNT - 1))
CRC_MOV %1, %1, LAST + 2
xor %1, %2
%else
CRC_XOR %2, %1, LAST + 2
%endif
%endmacro
; + 4 for prefetching next 4-bytes after current iteration
NUM_BYTES_LIMIT equ (NUM_WORDS * 4 * UNROLL_CNT + 4)
ALIGN_MASK equ 3
%define NUM_BYTES_LIMIT (NUM_WORDS * 4 * UNROLL_CNT + 4)
%define ALIGN_MASK 3
; MY_PROC @CatStr(CrcUpdateT, 12), 4
MY_PROC @CatStr(CrcUpdateT, %(NUM_WORDS * 4)), 4
MY_PROC AddNum(CrcUpdateT, NUM_WORDS * 4), 4
MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
ifdef x64
%if XBITS == 64
mov x0, REG_ABI_PARAM_0_x ; x0 = x1(win) / x7(linux)
mov rT, REG_ABI_PARAM_3 ; r5 = r9(win) / x1(linux)
mov rN, REG_ABI_PARAM_2 ; r7 = r8(win) / r2(linux)
; mov rD, REG_ABI_PARAM_1 ; r2 = r2(win)
if (IS_LINUX gt 0)
%if ABI == LINUX
mov rD, REG_ABI_PARAM_1 ; r2 = r6
endif
else
if (IS_CDECL gt 0)
%endif
%else
%if IS_CDECL == 1
mov x0, [r4 + crc_OFFS]
mov rD, [r4 + data_OFFS]
else
%else
mov x0, REG_ABI_PARAM_0_x
endif
%endif
mov rN, [r4 + size_OFFS]
mov rT, [r4 + table_OFFS]
endif
%endif
cmp rN, NUM_BYTES_LIMIT + ALIGN_MASK
jb crc_end
jb .crc_end
@@:
test rD_x, ALIGN_MASK ; test rD, ALIGN_MASK
jz @F
CRC1b
jmp @B
@@:
xor x0, dword ptr [rD]
xor x0, dword [rD]
lea rN, [rD + rN * 1 - (NUM_BYTES_LIMIT - 1)]
sub rD, rN
align 16
ALIGN 16
@@:
unr_index = 0
while unr_index lt UNROLL_CNT
if (unr_index and 1) eq 0
%assign unr_index 0
%rep UNROLL_CNT
%if (unr_index & 1) == 0
CRC_ITER x0, x1, unr_index
else
%else
CRC_ITER x1, x0, unr_index
endif
unr_index = unr_index + 1
endm
%endif
%assign unr_index unr_index+1
%endrep
add rD, NUM_WORDS * 4 * UNROLL_CNT
jnc @B
if 0
%if 0
; byte verson
add rD, rN
xor x0, dword ptr [rD]
xor x0, dword [rD]
add rN, NUM_BYTES_LIMIT - 1
else
%else
; 4-byte version
add rN, 4 * NUM_WORDS * UNROLL_CNT
sub rD, 4 * NUM_WORDS * UNROLL_CNT
@ -232,27 +230,26 @@ else
CRC_XOR x0, x6, 1
add rD, 4
if (NUM_WORDS * UNROLL_CNT) ne 1
%if (NUM_WORDS * UNROLL_CNT) != 1
jc @F
xor x0, [SRCDAT_4 0]
jmp @B
@@:
endif
%endif
add rD, rN
add rN, 4 - 1
endif
%endif
sub rN, rD
crc_end:
.crc_end:
test rN, rN
jz func_end
jz .func_end
@@:
CRC1b
jnz @B
func_end:
.func_end:
MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
MY_ENDP
MY_ENDP
end

File diff suppressed because it is too large Load diff

View file

@ -1,186 +1,176 @@
; LzFindOpt.asm -- ASM version of GetMatchesSpecN_2() function
; 2024-06-18: Igor Pavlov : Public domain
;
ifndef x64
; x64=1
; .err <x64_IS_REQUIRED>
endif
%include "7zAsm.inc"
include 7zAsm.asm
%if XBITS != 64
%fatal <x64_IS_REQUIRED>
%endif
MY_ASM_START
ifndef Z7_LZ_FIND_OPT_ASM_USE_SEGMENT
if (IS_LINUX gt 0)
Z7_LZ_FIND_OPT_ASM_USE_SEGMENT equ 1
else
Z7_LZ_FIND_OPT_ASM_USE_SEGMENT equ 1
endif
endif
%define Z7_LZ_FIND_OPT_ASM_USE_SEGMENT 1
ifdef Z7_LZ_FIND_OPT_ASM_USE_SEGMENT
_TEXT$LZFINDOPT SEGMENT ALIGN(64) 'CODE'
MY_ALIGN macro num:req
align num
; align 16
endm
else
MY_ALIGN macro num:req
%ifdef Z7_LZ_FIND_OPT_ASM_USE_SEGMENT
%macro MY_ALIGN 1
ALIGN %1
%endmacro
%else
%macro MY_ALIGN 1
; We expect that ".text" is aligned for 16-bytes.
; So we don't need large alignment inside our function.
align 16
endm
endif
ALIGN 16
%endmacro
%endif
MY_ALIGN_16 macro
%macro MY_ALIGN_16 0
MY_ALIGN 16
endm
%endmacro
MY_ALIGN_32 macro
%macro MY_ALIGN_32 0
MY_ALIGN 32
endm
%endmacro
MY_ALIGN_64 macro
%macro MY_ALIGN_64 0
MY_ALIGN 64
endm
%endmacro
t0_L equ x0_L
t0_x equ x0
t0 equ r0
t1_x equ x3
t1 equ r3
%define t0_L x0_L
%define t0_x x0
%define t0 r0
%define t1_x x3
%define t1 r3
cp_x equ t1_x
cp_r equ t1
m equ x5
m_r equ r5
len_x equ x6
len equ r6
diff_x equ x7
diff equ r7
len0 equ r10
len1_x equ x11
len1 equ r11
maxLen_x equ x12
maxLen equ r12
d equ r13
ptr0 equ r14
ptr1 equ r15
%define cp_x t1_x
%define cp_r t1
%define m x5
%define m_r r5
%define len_x x6
%define len r6
%define diff_x x7
%define diff r7
%define len0 r10
%define len1_x x11
%define len1 r11
%define maxLen_x x12
%define maxLen r12
%define d r13
%define ptr0 r14
%define ptr1 r15
d_lim equ m_r
cycSize equ len_x
hash_lim equ len0
delta1_x equ len1_x
delta1_r equ len1
delta_x equ maxLen_x
delta_r equ maxLen
hash equ ptr0
src equ ptr1
%define d_lim m_r
%define cycSize len_x
%define hash_lim len0
%define delta1_x len1_x
%define delta1_r len1
%define delta_x maxLen_x
%define delta_r maxLen
%define hash ptr0
%define src ptr1
if (IS_LINUX gt 0)
%if ABI == LINUX
; r1 r2 r8 r9 : win32
; r7 r6 r2 r1 r8 r9 : linux
lenLimit equ r8
lenLimit_x equ x8
; pos_r equ r2
pos equ x2
cur equ r1
son equ r9
%define lenLimit r8
%define lenLimit_x x8
; %define pos_r r2
%define pos x2
%define cur r1
%define son r9
else
%else
lenLimit equ REG_ABI_PARAM_2
lenLimit_x equ REG_ABI_PARAM_2_x
pos equ REG_ABI_PARAM_1_x
cur equ REG_ABI_PARAM_0
son equ REG_ABI_PARAM_3
%define lenLimit REG_ABI_PARAM_2
%define lenLimit_x REG_ABI_PARAM_2_x
%define pos REG_ABI_PARAM_1_x
%define cur REG_ABI_PARAM_0
%define son REG_ABI_PARAM_3
endif
%endif
if (IS_LINUX gt 0)
maxLen_OFFS equ (REG_SIZE * (6 + 1))
else
cutValue_OFFS equ (REG_SIZE * (8 + 1 + 4))
d_OFFS equ (REG_SIZE + cutValue_OFFS)
maxLen_OFFS equ (REG_SIZE + d_OFFS)
endif
hash_OFFS equ (REG_SIZE + maxLen_OFFS)
limit_OFFS equ (REG_SIZE + hash_OFFS)
size_OFFS equ (REG_SIZE + limit_OFFS)
cycPos_OFFS equ (REG_SIZE + size_OFFS)
cycSize_OFFS equ (REG_SIZE + cycPos_OFFS)
posRes_OFFS equ (REG_SIZE + cycSize_OFFS)
%if ABI == LINUX
%define maxLen_OFFS (REG_SIZE * (6 + 1))
%else
%define cutValue_OFFS (REG_SIZE * (8 + 1 + 4))
%define d_OFFS (REG_SIZE + cutValue_OFFS)
%define maxLen_OFFS (REG_SIZE + d_OFFS)
%endif
%define hash_OFFS (REG_SIZE + maxLen_OFFS)
%define limit_OFFS (REG_SIZE + hash_OFFS)
%define size_OFFS (REG_SIZE + limit_OFFS)
%define cycPos_OFFS (REG_SIZE + size_OFFS)
%define cycSize_OFFS (REG_SIZE + cycPos_OFFS)
%define posRes_OFFS (REG_SIZE + cycSize_OFFS)
if (IS_LINUX gt 0)
else
cutValue_PAR equ [r0 + cutValue_OFFS]
d_PAR equ [r0 + d_OFFS]
endif
maxLen_PAR equ [r0 + maxLen_OFFS]
hash_PAR equ [r0 + hash_OFFS]
limit_PAR equ [r0 + limit_OFFS]
size_PAR equ [r0 + size_OFFS]
cycPos_PAR equ [r0 + cycPos_OFFS]
cycSize_PAR equ [r0 + cycSize_OFFS]
posRes_PAR equ [r0 + posRes_OFFS]
%if ABI == WINDOWS
%define cutValue_PAR [r0 + cutValue_OFFS]
%define d_PAR [r0 + d_OFFS]
%endif
%define maxLen_PAR [r0 + maxLen_OFFS]
%define hash_PAR [r0 + hash_OFFS]
%define limit_PAR [r0 + limit_OFFS]
%define size_PAR [r0 + size_OFFS]
%define cycPos_PAR [r0 + cycPos_OFFS]
%define cycSize_PAR [r0 + cycSize_OFFS]
%define posRes_PAR [r0 + posRes_OFFS]
cutValue_VAR equ DWORD PTR [r4 + 8 * 0]
cutValueCur_VAR equ DWORD PTR [r4 + 8 * 0 + 4]
cycPos_VAR equ DWORD PTR [r4 + 8 * 1 + 0]
cycSize_VAR equ DWORD PTR [r4 + 8 * 1 + 4]
hash_VAR equ QWORD PTR [r4 + 8 * 2]
limit_VAR equ QWORD PTR [r4 + 8 * 3]
size_VAR equ QWORD PTR [r4 + 8 * 4]
distances equ QWORD PTR [r4 + 8 * 5]
maxLen_VAR equ QWORD PTR [r4 + 8 * 6]
%define cutValue_VAR DWORD [r4 + 8 * 0]
%define cutValueCur_VAR DWORD [r4 + 8 * 0 + 4]
%define cycPos_VAR DWORD [r4 + 8 * 1 + 0]
%define cycSize_VAR DWORD [r4 + 8 * 1 + 4]
%define hash_VAR QWORD [r4 + 8 * 2]
%define limit_VAR QWORD [r4 + 8 * 3]
%define size_VAR QWORD [r4 + 8 * 4]
%define distances QWORD [r4 + 8 * 5]
%define maxLen_VAR QWORD [r4 + 8 * 6]
Old_RSP equ QWORD PTR [r4 + 8 * 7]
LOCAL_SIZE equ 8 * 8
%define Old_RSP QWORD [r4 + 8 * 7]
%define LOCAL_SIZE 8 * 8
COPY_VAR_32 macro dest_var, src_var
mov x3, src_var
mov dest_var, x3
endm
%macro COPY_VAR_32 2 ; dest, src
mov x3, %2
mov %1, x3
%endmacro
COPY_VAR_64 macro dest_var, src_var
mov r3, src_var
mov dest_var, r3
endm
%macro COPY_VAR_64 2 ; dest, src
mov r3, %2
mov %1, r3
%endmacro
ifdef Z7_LZ_FIND_OPT_ASM_USE_SEGMENT
; MY_ALIGN_64
else
%ifdef Z7_LZ_FIND_OPT_ASM_USE_SEGMENT
; MY_ALIGN_64
[section .text$LZFINDOPT align=64 exec]
%else
MY_ALIGN_16
endif
%endif
MY_PROC GetMatchesSpecN_2, 13
MY_PUSH_PRESERVED_ABI_REGS
MY_PUSH_PRESERVED_ABI_REGS
mov r0, RSP
lea r3, [r0 - LOCAL_SIZE]
and r3, -64
mov RSP, r3
mov Old_RSP, r0
if (IS_LINUX gt 0)
%if ABI == LINUX
mov d, REG_ABI_PARAM_5 ; r13 = r9
mov cutValue_VAR, REG_ABI_PARAM_4_x ; = r8
mov son, REG_ABI_PARAM_3 ; r9 = r1
mov r8, REG_ABI_PARAM_2 ; r8 = r2
mov pos, REG_ABI_PARAM_1_x ; r2 = x6
mov r1, REG_ABI_PARAM_0 ; r1 = r7
else
%else
COPY_VAR_32 cutValue_VAR, cutValue_PAR
mov d, d_PAR
endif
%endif
COPY_VAR_64 limit_VAR, limit_PAR
@ -202,62 +192,62 @@ endif
sub t0, lenLimit
mov maxLen_VAR, t0
jmp main_loop
jmp .main_loop
MY_ALIGN_64
fill_empty:
.fill_empty:
; ptr0 = *ptr1 = kEmptyHashValue;
mov QWORD PTR [ptr1], 0
mov QWORD [ptr1], 0
inc pos
inc cp_x
mov DWORD PTR [d - 4], 0
mov DWORD [d - 4], 0
cmp d, limit_VAR
jae fin
jae .fin
cmp hash, hash_lim
je fin
je .fin
; MY_ALIGN_64
main_loop:
.main_loop:
; UInt32 delta = *hash++;
mov diff_x, [hash] ; delta
add hash, 4
; mov cycPos_VAR, cp_x
inc cur
add d, 4
mov m, pos
sub m, diff_x; ; matchPos
; CLzRef *ptr1 = son + ((size_t)(pos) << 1) - CYC_TO_POS_OFFSET * 2;
lea ptr1, [son + 8 * cp_r]
; mov cycSize, cycSize_VAR
cmp pos, cycSize
jb directMode ; if (pos < cycSize_VAR)
jb .directMode ; if (pos < cycSize_VAR)
; CYC MODE
cmp diff_x, cycSize
jae fill_empty ; if (delta >= cycSize_VAR)
jae .fill_empty ; if (delta >= cycSize_VAR)
xor t0_x, t0_x
mov cycPos_VAR, cp_x
sub cp_x, diff_x
; jae prepare_for_tree_loop
; jae .prepare_for_tree_loop
; add cp_x, cycSize
cmovb t0_x, cycSize
add cp_x, t0_x ; cp_x += (cycPos < delta ? cycSize : 0)
jmp prepare_for_tree_loop
directMode:
jmp .prepare_for_tree_loop
.directMode:
cmp diff_x, pos
je fill_empty ; if (delta == pos)
jae fin_error ; if (delta >= pos)
je .fill_empty ; if (delta == pos)
jae .fin_error ; if (delta >= pos)
mov cycPos_VAR, cp_x
mov cp_x, m
prepare_for_tree_loop:
.prepare_for_tree_loop:
mov len0, lenLimit
mov hash_VAR, hash
; CLzRef *ptr0 = son + ((size_t)(pos) << 1) - CYC_TO_POS_OFFSET * 2 + 1;
@ -273,7 +263,7 @@ prepare_for_tree_loop:
mov cutValueCur_VAR, t0_x
MY_ALIGN_32
tree_loop:
.tree_loop:
neg diff
mov len, len0
cmp len1, len0
@ -281,54 +271,54 @@ tree_loop:
add diff, cur
mov t0_x, [son + cp_r * 8] ; prefetch
movzx t0_x, BYTE PTR [diff + 1 * len]
movzx t0_x, BYTE [diff + 1 * len]
lea cp_r, [son + cp_r * 8]
cmp [cur + 1 * len], t0_L
je matched_1
jb left_0
je .matched_1
jb .left_0
mov [ptr1], m
mov m, [cp_r + 4]
lea ptr1, [cp_r + 4]
sub diff, cur ; FIX32
jmp next_node
jmp .next_node
MY_ALIGN_32
left_0:
.left_0:
mov [ptr0], m
mov m, [cp_r]
mov ptr0, cp_r
sub diff, cur ; FIX32
; jmp next_node
; jmp .next_node
; ------------ NEXT NODE ------------
; MY_ALIGN_32
next_node:
.next_node:
mov cycSize, cycSize_VAR
dec cutValueCur_VAR
je finish_tree
je .finish_tree
add diff_x, pos ; prev_match = pos + diff
cmp m, diff_x
jae fin_error ; if (new_match >= prev_match)
jae .fin_error ; if (new_match >= prev_match)
mov diff_x, pos
sub diff_x, m ; delta = pos - new_match
cmp pos, cycSize
jae cyc_mode_2 ; if (pos >= cycSize)
jae .cyc_mode_2 ; if (pos >= cycSize)
mov cp_x, m
test m, m
jne tree_loop ; if (m != 0)
finish_tree:
jne .tree_loop ; if (m != 0)
.finish_tree:
; ptr0 = *ptr1 = kEmptyHashValue;
mov DWORD PTR [ptr0], 0
mov DWORD PTR [ptr1], 0
mov DWORD [ptr0], 0
mov DWORD [ptr1], 0
inc pos
; _distances[-1] = (UInt32)(d - _distances);
mov t0, distances
mov t1, d
@ -337,75 +327,75 @@ finish_tree:
mov [t0 - 4], t1_x
cmp d, limit_VAR
jae fin ; if (d >= limit)
jae .fin ; if (d >= limit)
mov cp_x, cycPos_VAR
mov hash, hash_VAR
mov hash_lim, size_VAR
inc cp_x
cmp hash, hash_lim
jne main_loop ; if (hash != size)
jmp fin
jne .main_loop ; if (hash != size)
jmp .fin
MY_ALIGN_32
cyc_mode_2:
.cyc_mode_2:
cmp diff_x, cycSize
jae finish_tree ; if (delta >= cycSize)
jae .finish_tree ; if (delta >= cycSize)
mov cp_x, cycPos_VAR
xor t0_x, t0_x
sub cp_x, diff_x ; cp_x = cycPos - delta
cmovb t0_x, cycSize
add cp_x, t0_x ; cp_x += (cycPos < delta ? cycSize : 0)
jmp tree_loop
jmp .tree_loop
MY_ALIGN_32
matched_1:
.matched_1:
inc len
; cmp len_x, lenLimit_x
je short lenLimit_reach
movzx t0_x, BYTE PTR [diff + 1 * len]
je short .lenLimit_reach
movzx t0_x, BYTE [diff + 1 * len]
cmp [cur + 1 * len], t0_L
jne mismatch
jne .mismatch
MY_ALIGN_32
match_loop:
.match_loop:
; while (++len != lenLimit) (len[diff] != len[0]) ;
inc len
; cmp len_x, lenLimit_x
je short lenLimit_reach
movzx t0_x, BYTE PTR [diff + 1 * len]
cmp BYTE PTR [cur + 1 * len], t0_L
je match_loop
je short .lenLimit_reach
movzx t0_x, BYTE [diff + 1 * len]
cmp BYTE [cur + 1 * len], t0_L
je .match_loop
mismatch:
jb left_2
.mismatch:
jb .left_2
mov [ptr1], m
mov m, [cp_r + 4]
lea ptr1, [cp_r + 4]
mov len1, len
jmp max_update
jmp .max_update
MY_ALIGN_32
left_2:
.left_2:
mov [ptr0], m
mov m, [cp_r]
mov ptr0, cp_r
mov len0, len
max_update:
.max_update:
sub diff, cur ; restore diff
cmp maxLen, len
jae next_node
jae .next_node
mov maxLen, len
add len, lenLimit
mov [d], len_x
@ -413,13 +403,12 @@ max_update:
not t0_x
mov [d + 4], t0_x
add d, 8
jmp next_node
jmp .next_node
MY_ALIGN_32
lenLimit_reach:
.lenLimit_reach:
mov delta_r, cur
sub delta_r, diff
@ -453,17 +442,17 @@ lenLimit_reach:
; if (hash == size || *hash != delta || lenLimit[diff] != lenLimit[0] || d >= limit)
; break;
cmp hash, hash_lim
je fin
je .fin
cmp d, d_lim
jae fin
jae .fin
cmp delta_x, [hash]
jne main_loop
movzx t0_x, BYTE PTR [diff]
jne .main_loop
movzx t0_x, BYTE [diff]
cmp [cur], t0_L
jne main_loop
jne .main_loop
; jmp .main_loop ; bypass for debug
; jmp main_loop ; bypass for debug
mov cycPos_VAR, cp_x
shl len, 3 ; cycSize * 8
sub diff, cur ; restore diff
@ -475,13 +464,13 @@ lenLimit_reach:
add src, t0
add len, son ; len = son + cycSize * 8
MY_ALIGN_32
long_loop:
.long_loop:
add hash, 4
; *(UInt64 *)(void *)ptr = ((const UInt64 *)(const void *)ptr)[diff];
mov t0, [src]
add src, 8
mov [cp_r], t0
@ -489,7 +478,7 @@ long_loop:
cmp src, len
cmove src, son ; if end of (son) buffer is reached, we wrap to begin
mov DWORD PTR [d], 2
mov DWORD [d], 2
mov [d + 4], lenLimit_x
mov [d + 8], delta1_x
add d, 12
@ -497,44 +486,38 @@ long_loop:
inc cur
cmp hash, hash_lim
je long_footer
je .long_footer
cmp delta_x, [hash]
jne long_footer
movzx t0_x, BYTE PTR [diff + 1 * cur]
jne .long_footer
movzx t0_x, BYTE [diff + 1 * cur]
cmp [cur], t0_L
jne long_footer
jne .long_footer
cmp d, d_lim
jb long_loop
jb .long_loop
long_footer:
.long_footer:
sub cp_r, son
shr cp_r, 3
add pos, cp_x
sub pos, cycPos_VAR
mov cycSize, cycSize_VAR
cmp d, d_lim
jae fin
jae .fin
cmp hash, hash_lim
jne main_loop
jmp fin
jne .main_loop
jmp .fin
fin_error:
.fin_error:
xor d, d
fin:
.fin:
mov RSP, Old_RSP
mov t0, [r4 + posRes_OFFS]
mov [t0], pos
mov r0, d
MY_POP_PRESERVED_ABI_REGS
MY_ENDP
MY_POP_PRESERVED_ABI_REGS
MY_ENDP
ifdef Z7_LZ_FIND_OPT_ASM_USE_SEGMENT
_TEXT$LZFINDOPT ENDS
endif
end

File diff suppressed because it is too large Load diff

View file

@ -1,263 +1,196 @@
; Sha1Opt.asm -- SHA-1 optimized code for SHA-1 x86 hardware instructions
; 2024-06-16 : Igor Pavlov : Public domain
include 7zAsm.asm
%include "7zAsm.inc"
MY_ASM_START
%if XBITS == 64
%define rNum REG_ABI_PARAM_2
%if ABI == WINDOWS
%define LOCAL_SIZE (16 * 2)
%endif
%else
%define rNum r0
%define LOCAL_SIZE (16 * 1)
%endif
%define rState REG_ABI_PARAM_0
%define rData REG_ABI_PARAM_1
CONST SEGMENT READONLY
align 16
Reverse_Endian_Mask db 15,14,13,12, 11,10,9,8, 7,6,5,4, 3,2,1,0
CONST ENDS
; _TEXT$SHA1OPT SEGMENT 'CODE'
ifndef x64
.686
.xmm
endif
ifdef x64
rNum equ REG_ABI_PARAM_2
if (IS_LINUX eq 0)
LOCAL_SIZE equ (16 * 2)
endif
else
rNum equ r0
LOCAL_SIZE equ (16 * 1)
endif
rState equ REG_ABI_PARAM_0
rData equ REG_ABI_PARAM_1
MY_sha1rnds4 macro a1, a2, imm
db 0fH, 03aH, 0ccH, (0c0H + a1 * 8 + a2), imm
endm
MY_SHA_INSTR macro cmd, a1, a2
db 0fH, 038H, cmd, (0c0H + a1 * 8 + a2)
endm
cmd_sha1nexte equ 0c8H
cmd_sha1msg1 equ 0c9H
cmd_sha1msg2 equ 0caH
MY_sha1nexte macro a1, a2
MY_SHA_INSTR cmd_sha1nexte, a1, a2
endm
MY_sha1msg1 macro a1, a2
MY_SHA_INSTR cmd_sha1msg1, a1, a2
endm
MY_sha1msg2 macro a1, a2
MY_SHA_INSTR cmd_sha1msg2, a1, a2
endm
MY_PROLOG macro
ifdef x64
if (IS_LINUX eq 0)
%macro MY_PROLOG 0
%if XBITS == 64
%if ABI == WINDOWS
movdqa [r4 + 8], xmm6
movdqa [r4 + 8 + 16], xmm7
sub r4, LOCAL_SIZE + 8
movdqa [r4 ], xmm8
movdqa [r4 + 16], xmm9
endif
else ; x86
if (IS_CDECL gt 0)
%endif
%else ; x86
%if IS_CDECL == 1
mov rState, [r4 + REG_SIZE * 1]
mov rData, [r4 + REG_SIZE * 2]
mov rNum, [r4 + REG_SIZE * 3]
else ; fastcall
%else ; fastcall
mov rNum, [r4 + REG_SIZE * 1]
endif
%endif
push r5
mov r5, r4
and r4, -16
sub r4, LOCAL_SIZE
endif
endm
%endif
%endmacro
MY_EPILOG macro
ifdef x64
if (IS_LINUX eq 0)
%macro MY_EPILOG 0
%if XBITS == 64
%if ABI == WINDOWS
movdqa xmm8, [r4]
movdqa xmm9, [r4 + 16]
add r4, LOCAL_SIZE + 8
movdqa xmm6, [r4 + 8]
movdqa xmm7, [r4 + 8 + 16]
endif
else ; x86
%endif
%else ; x86
mov r4, r5
pop r5
endif
MY_ENDP
endm
%endif
MY_ENDP
%endmacro
e0_N equ 0
e1_N equ 1
abcd_N equ 2
e0_save_N equ 3
w_regs equ 4
%define e0_N 0
%define e1_N 1
%define abcd_N 2
%define e0_save_N 3
%define w_regs 4
e0 equ @CatStr(xmm, %e0_N)
e1 equ @CatStr(xmm, %e1_N)
abcd equ @CatStr(xmm, %abcd_N)
e0_save equ @CatStr(xmm, %e0_save_N)
%define e0 XMM_REG(e0_N)
%define e1 XMM_REG(e1_N)
%define abcd XMM_REG(abcd_N)
%define e0_save XMM_REG(e0_save_N)
ifdef x64
abcd_save equ xmm8
mask2 equ xmm9
else
abcd_save equ [r4]
mask2 equ e1
endif
%if XBITS == 64
%define abcd_save xmm8
%define mask2 xmm9
%else
%define abcd_save [r4]
%define mask2 e1
%endif
LOAD_MASK macro
movdqa mask2, XMMWORD PTR Reverse_Endian_Mask
endm
%macro LOAD_MASK 0
movdqa mask2, [.Reverse_Endian_Mask]
%endmacro
LOAD_W macro k:req
movdqu @CatStr(xmm, %(w_regs + k)), [rData + (16 * (k))]
pshufb @CatStr(xmm, %(w_regs + k)), mask2
endm
%macro LOAD_W 1
movdqu XMM_REG(w_regs + %1), [rData + 16 * %1]
pshufb XMM_REG(w_regs + %1), mask2
%endmacro
; pre2 can be 2 or 3 (recommended)
pre2 equ 3
pre1 equ (pre2 + 1)
%define pre2 3
%define pre1 (pre2 + 1)
NUM_ROUNDS4 equ 20
RND4 macro k
movdqa @CatStr(xmm, %(e0_N + ((k + 1) mod 2))), abcd
MY_sha1rnds4 abcd_N, (e0_N + (k mod 2)), k / 5
nextM = (w_regs + ((k + 1) mod 4))
if (k EQ NUM_ROUNDS4 - 1)
nextM = e0_save_N
endif
MY_sha1nexte (e0_N + ((k + 1) mod 2)), nextM
if (k GE (4 - pre2)) AND (k LT (NUM_ROUNDS4 - pre2))
pxor @CatStr(xmm, %(w_regs + ((k + pre2) mod 4))), @CatStr(xmm, %(w_regs + ((k + pre2 - 2) mod 4)))
endif
if (k GE (4 - pre1)) AND (k LT (NUM_ROUNDS4 - pre1))
MY_sha1msg1 (w_regs + ((k + pre1) mod 4)), (w_regs + ((k + pre1 - 3) mod 4))
endif
if (k GE (4 - pre2)) AND (k LT (NUM_ROUNDS4 - pre2))
MY_sha1msg2 (w_regs + ((k + pre2) mod 4)), (w_regs + ((k + pre2 - 1) mod 4))
endif
endm
%define NUM_ROUNDS4 20
REVERSE_STATE macro
; abcd ; dcba
; e0 ; 000e
pshufd abcd, abcd, 01bH ; abcd
pshufd e0, e0, 01bH ; e000
endm
%macro RND4 1
XMMOP movdqa, (e0_N + ((%1 + 1) mod 2)), abcd_N
XMMOP sha1rnds4, abcd_N, (e0_N + (%1 mod 2)), %1 / 5
%assign nextM w_regs + ((%1 + 1) mod 4)
%if (%1 == NUM_ROUNDS4 - 1)
%assign nextM e0_save_N
%endif
XMMOP sha1nexte, (e0_N + ((%1 + 1) mod 2)), nextM
%if (%1 >= (4 - pre2)) && (%1 < (NUM_ROUNDS4 - pre2))
XMMOP pxor, (w_regs + ((%1 + pre2) mod 4)), (w_regs + ((%1 + pre2 - 2) mod 4))
%endif
%if (%1 >= (4 - pre1)) && (%1 < (NUM_ROUNDS4 - pre1))
XMMOP sha1msg1, (w_regs + ((%1 + pre1) mod 4)), (w_regs + ((%1 + pre1 - 3) mod 4))
%endif
%if (%1 >= (4 - pre2)) && (%1 < (NUM_ROUNDS4 - pre2))
XMMOP sha1msg2, (w_regs + ((%1 + pre2) mod 4)), (w_regs + ((%1 + pre2 - 1) mod 4))
%endif
%endmacro
%macro REVERSE_STATE 0
; abcd ; dcba
; e0 ; 000e
pshufd abcd, abcd, 1BH ; abcd
pshufd e0, e0, 1BH ; e000
%endmacro
MY_PROC Sha1_UpdateBlocks_HW, 3
MY_PROLOG
MY_PROLOG
cmp rNum, 0
je end_c
je .end_c
movdqu abcd, [rState] ; dcba
movd e0, dword ptr [rState + 16] ; 000e
movdqu abcd, [rState] ; dcba
movd e0, dword [rState + 16] ; 000e
REVERSE_STATE
ifdef x64
LOAD_MASK
endif
align 16
nextBlock:
%if XBITS == 64
LOAD_MASK
%endif
ALIGN 16
.nextBlock:
movdqa abcd_save, abcd
movdqa e0_save, e0
ifndef x64
%if XBITS == 32
LOAD_MASK
endif
%endif
LOAD_W 0
LOAD_W 1
LOAD_W 2
LOAD_W 3
paddd e0, @CatStr(xmm, %(w_regs))
k = 0
rept NUM_ROUNDS4
paddd e0, XMM_REG(w_regs)
%assign k 0
%rep NUM_ROUNDS4
RND4 k
k = k + 1
endm
%assign k k+1
%endrep
paddd abcd, abcd_save
add rData, 64
sub rNum, 1
jnz nextBlock
jnz .nextBlock
REVERSE_STATE
movdqu [rState], abcd
movd dword ptr [rState + 16], e0
end_c:
MY_EPILOG
movd dword [rState + 16], e0
; _TEXT$SHA1OPT ENDS
.end_c:
MY_EPILOG
[section READONLY]
ALIGN 16
.Reverse_Endian_Mask db 15,14,13,12, 11,10,9,8, 7,6,5,4, 3,2,1,0
end

View file

@ -1,212 +1,148 @@
; Sha256Opt.asm -- SHA-256 optimized code for SHA-256 x86 hardware instructions
; 2024-06-16 : Igor Pavlov : Public domain
include 7zAsm.asm
%include "7zAsm.inc"
MY_ASM_START
; .data
; public K
; we can use external SHA256_K_ARRAY defined in Sha256.c
; but we must guarantee that SHA256_K_ARRAY is aligned for 16-bytes
COMMENT @
ifdef x64
K_CONST equ SHA256_K_ARRAY
else
K_CONST equ _SHA256_K_ARRAY
endif
EXTRN K_CONST:xmmword
@
; extern SHA256_K_ARRAY
; %define .K_CONST SHA256_K_ARRAY
CONST SEGMENT READONLY
align 16
Reverse_Endian_Mask db 3,2,1,0, 7,6,5,4, 11,10,9,8, 15,14,13,12
; COMMENT @
align 16
K_CONST \
DD 0428a2f98H, 071374491H, 0b5c0fbcfH, 0e9b5dba5H
DD 03956c25bH, 059f111f1H, 0923f82a4H, 0ab1c5ed5H
DD 0d807aa98H, 012835b01H, 0243185beH, 0550c7dc3H
DD 072be5d74H, 080deb1feH, 09bdc06a7H, 0c19bf174H
DD 0e49b69c1H, 0efbe4786H, 00fc19dc6H, 0240ca1ccH
DD 02de92c6fH, 04a7484aaH, 05cb0a9dcH, 076f988daH
DD 0983e5152H, 0a831c66dH, 0b00327c8H, 0bf597fc7H
DD 0c6e00bf3H, 0d5a79147H, 006ca6351H, 014292967H
DD 027b70a85H, 02e1b2138H, 04d2c6dfcH, 053380d13H
DD 0650a7354H, 0766a0abbH, 081c2c92eH, 092722c85H
DD 0a2bfe8a1H, 0a81a664bH, 0c24b8b70H, 0c76c51a3H
DD 0d192e819H, 0d6990624H, 0f40e3585H, 0106aa070H
DD 019a4c116H, 01e376c08H, 02748774cH, 034b0bcb5H
DD 0391c0cb3H, 04ed8aa4aH, 05b9cca4fH, 0682e6ff3H
DD 0748f82eeH, 078a5636fH, 084c87814H, 08cc70208H
DD 090befffaH, 0a4506cebH, 0bef9a3f7H, 0c67178f2H
; @
CONST ENDS
; _TEXT$SHA256OPT SEGMENT 'CODE'
ifndef x64
.686
.xmm
endif
; jwasm-based assemblers for linux and linker from new versions of binutils
; can generate incorrect code for load [ARRAY + offset] instructions.
; 22.00: we load K_CONST offset to (rTable) register to avoid jwasm+binutils problem
rTable equ r0
; rTable equ K_CONST
ifdef x64
rNum equ REG_ABI_PARAM_2
if (IS_LINUX eq 0)
LOCAL_SIZE equ (16 * 2)
endif
else
rNum equ r3
LOCAL_SIZE equ (16 * 1)
endif
; 22.00: we load .K_CONST offset to (rTable) register to avoid jwasm+binutils problem
%define rTable r0
; %define rTable .K_CONST
rState equ REG_ABI_PARAM_0
rData equ REG_ABI_PARAM_1
%if XBITS == 64
%define rNum REG_ABI_PARAM_2
%if ABI == WINDOWS
%define LOCAL_SIZE (16 * 2)
%endif
%else
%define rNum r3
%define LOCAL_SIZE (16 * 1)
%endif
%define rState REG_ABI_PARAM_0
%define rData REG_ABI_PARAM_1
MY_SHA_INSTR macro cmd, a1, a2
db 0fH, 038H, cmd, (0c0H + a1 * 8 + a2)
endm
cmd_sha256rnds2 equ 0cbH
cmd_sha256msg1 equ 0ccH
cmd_sha256msg2 equ 0cdH
MY_sha256rnds2 macro a1, a2
MY_SHA_INSTR cmd_sha256rnds2, a1, a2
endm
MY_sha256msg1 macro a1, a2
MY_SHA_INSTR cmd_sha256msg1, a1, a2
endm
MY_sha256msg2 macro a1, a2
MY_SHA_INSTR cmd_sha256msg2, a1, a2
endm
MY_PROLOG macro
ifdef x64
if (IS_LINUX eq 0)
%macro MY_PROLOG 0
%if XBITS == 64
%if ABI == WINDOWS
movdqa [r4 + 8], xmm6
movdqa [r4 + 8 + 16], xmm7
sub r4, LOCAL_SIZE + 8
movdqa [r4 ], xmm8
movdqa [r4 + 16], xmm9
endif
else ; x86
%endif
%else ; x86
push r3
push r5
mov r5, r4
NUM_PUSH_REGS equ 2
PARAM_OFFSET equ (REG_SIZE * (1 + NUM_PUSH_REGS))
if (IS_CDECL gt 0)
%define NUM_PUSH_REGS 2
%define PARAM_OFFSET (REG_SIZE * (1 + NUM_PUSH_REGS))
%if IS_CDECL == 1
mov rState, [r4 + PARAM_OFFSET]
mov rData, [r4 + PARAM_OFFSET + REG_SIZE * 1]
mov rNum, [r4 + PARAM_OFFSET + REG_SIZE * 2]
else ; fastcall
%else ; fastcall
mov rNum, [r4 + PARAM_OFFSET]
endif
%endif
and r4, -16
sub r4, LOCAL_SIZE
endif
endm
%endif
%endmacro
MY_EPILOG macro
ifdef x64
if (IS_LINUX eq 0)
%macro MY_EPILOG 0
%if XBITS == 64
%if ABI == WINDOWS
movdqa xmm8, [r4]
movdqa xmm9, [r4 + 16]
add r4, LOCAL_SIZE + 8
movdqa xmm6, [r4 + 8]
movdqa xmm7, [r4 + 8 + 16]
endif
else ; x86
%endif
%else ; x86
mov r4, r5
pop r5
pop r3
endif
%endif
MY_ENDP
endm
%endmacro
msg equ xmm0
tmp equ xmm0
state0_N equ 2
state1_N equ 3
w_regs equ 4
%define msg_N 0
%define tmp_N 0
%define state0_N 2
%define state1_N 3
%define w_regs 4
%define msg XMM_REG(msg_N)
%define tmp XMM_REG(tmp_N)
%define state1_save xmm1
%define state0 XMM_REG(state0_N)
%define state1 XMM_REG(state1_N)
state1_save equ xmm1
state0 equ @CatStr(xmm, %state0_N)
state1 equ @CatStr(xmm, %state1_N)
%if XBITS == 64
%define state0_save xmm8
%define mask2 xmm9
%else
%define state0_save [r4]
%define mask2 xmm0
%endif
%macro LOAD_MASK 0
movdqa mask2, [.Reverse_Endian_Mask]
%endmacro
ifdef x64
state0_save equ xmm8
mask2 equ xmm9
else
state0_save equ [r4]
mask2 equ xmm0
endif
LOAD_MASK macro
movdqa mask2, XMMWORD PTR Reverse_Endian_Mask
endm
LOAD_W macro k:req
movdqu @CatStr(xmm, %(w_regs + k)), [rData + (16 * (k))]
pshufb @CatStr(xmm, %(w_regs + k)), mask2
endm
%macro LOAD_W 1
movdqu XMM_REG(w_regs + %1), [rData + 16 * %1]
pshufb XMM_REG(w_regs + %1), mask2
%endmacro
; pre1 <= 4 && pre2 >= 1 && pre1 > pre2 && (pre1 - pre2) <= 1
pre1 equ 3
pre2 equ 2
%define pre1 3
%define pre2 2
RND4 macro k
movdqa msg, xmmword ptr [rTable + (k) * 16]
paddd msg, @CatStr(xmm, %(w_regs + ((k + 0) mod 4)))
MY_sha256rnds2 state0_N, state1_N
pshufd msg, msg, 0eH
if (k GE (4 - pre1)) AND (k LT (16 - pre1))
%macro RND4 1
movdqa msg, [rTable + (%1) * 16]
XMMOP paddd, msg_N, (w_regs + ((%1 + 0) mod 4))
sha256rnds2 state0, state1
pshufd msg, msg, 0eH
%if (%1 >= (4 - pre1)) && (%1 < (16 - pre1))
; w4[0] = msg1(w4[-4], w4[-3])
MY_sha256msg1 (w_regs + ((k + pre1) mod 4)), (w_regs + ((k + pre1 - 3) mod 4))
endif
MY_sha256rnds2 state1_N, state0_N
XMMOP sha256msg1, (w_regs + ((%1 + pre1) mod 4)), (w_regs + ((%1 + pre1 - 3) mod 4))
%endif
if (k GE (4 - pre2)) AND (k LT (16 - pre2))
movdqa tmp, @CatStr(xmm, %(w_regs + ((k + pre2 - 1) mod 4)))
palignr tmp, @CatStr(xmm, %(w_regs + ((k + pre2 - 2) mod 4))), 4
paddd @CatStr(xmm, %(w_regs + ((k + pre2) mod 4))), tmp
sha256rnds2 state1, state0
%if (%1 >= (4 - pre2)) && (%1 < (16 - pre2))
XMMOP movdqa, tmp_N, (w_regs + ((%1 + pre2 - 1) mod 4))
XMMOP palignr, tmp_N, (w_regs + ((%1 + pre2 - 2) mod 4)), 4
XMMOP paddd, (w_regs + ((%1 + pre2) mod 4)), tmp_N
; w4[0] = msg2(w4[0], w4[-1])
MY_sha256msg2 %(w_regs + ((k + pre2) mod 4)), %(w_regs + ((k + pre2 - 1) mod 4))
endif
endm
XMMOP sha256msg2, (w_regs + ((%1 + pre2) mod 4)), (w_regs + ((%1 + pre2 - 1) mod 4))
%endif
%endmacro
REVERSE_STATE macro
%macro REVERSE_STATE 0
; state0 ; dcba
; state1 ; hgfe
pshufd tmp, state0, 01bH ; abcd
@ -214,62 +150,85 @@ REVERSE_STATE macro
movdqa state1, state0 ; efgh
punpcklqdq state0, tmp ; cdgh
punpckhqdq state1, tmp ; abef
endm
%endmacro
MY_PROC Sha256_UpdateBlocks_HW, 3
MY_PROLOG
MY_PROLOG
lea rTable, [K_CONST]
lea rTable, [.K_CONST]
cmp rNum, 0
je end_c
je .end_c
movdqu state0, [rState] ; dcba
movdqu state1, [rState + 16] ; hgfe
REVERSE_STATE
ifdef x64
%if XBITS == 64
LOAD_MASK
endif
%endif
align 16
nextBlock:
.nextBlock:
movdqa state0_save, state0
movdqa state1_save, state1
ifndef x64
%if XBITS == 32
LOAD_MASK
endif
%endif
LOAD_W 0
LOAD_W 1
LOAD_W 2
LOAD_W 3
k = 0
rept 16
%assign k 0
%rep 16
RND4 k
k = k + 1
endm
%assign k k+1
%endrep
paddd state0, state0_save
paddd state1, state1_save
add rData, 64
sub rNum, 1
jnz nextBlock
jnz .nextBlock
REVERSE_STATE
movdqu [rState], state0
movdqu [rState + 16], state1
end_c:
MY_EPILOG
; _TEXT$SHA256OPT ENDS
.end_c:
MY_EPILOG
[section READONLY]
ALIGN 16
.Reverse_Endian_Mask db 3,2,1,0, 7,6,5,4, 11,10,9,8, 15,14,13,12
ALIGN 16
.K_CONST:
DD 0428a2f98H, 071374491H, 0b5c0fbcfH, 0e9b5dba5H
DD 03956c25bH, 059f111f1H, 0923f82a4H, 0ab1c5ed5H
DD 0d807aa98H, 012835b01H, 0243185beH, 0550c7dc3H
DD 072be5d74H, 080deb1feH, 09bdc06a7H, 0c19bf174H
DD 0e49b69c1H, 0efbe4786H, 00fc19dc6H, 0240ca1ccH
DD 02de92c6fH, 04a7484aaH, 05cb0a9dcH, 076f988daH
DD 0983e5152H, 0a831c66dH, 0b00327c8H, 0bf597fc7H
DD 0c6e00bf3H, 0d5a79147H, 006ca6351H, 014292967H
DD 027b70a85H, 02e1b2138H, 04d2c6dfcH, 053380d13H
DD 0650a7354H, 0766a0abbH, 081c2c92eH, 092722c85H
DD 0a2bfe8a1H, 0a81a664bH, 0c24b8b70H, 0c76c51a3H
DD 0d192e819H, 0d6990624H, 0f40e3585H, 0106aa070H
DD 019a4c116H, 01e376c08H, 02748774cH, 034b0bcb5H
DD 0391c0cb3H, 04ed8aa4aH, 05b9cca4fH, 0682e6ff3H
DD 0748f82eeH, 078a5636fH, 084c87814H, 08cc70208H
DD 090befffaH, 0a4506cebH, 0bef9a3f7H, 0c67178f2H
end

File diff suppressed because it is too large Load diff

View file

@ -1,103 +1,106 @@
; XzCrc64Opt.asm -- CRC64 calculation : optimized version
; 2023-12-08 : Igor Pavlov : Public domain
include 7zAsm.asm
%include "7zAsm.inc"
MY_ASM_START
NUM_WORDS equ 3
%define NUM_WORDS 3
if (NUM_WORDS lt 1) or (NUM_WORDS gt 64)
.err <num_words_IS_INCORRECT>
endif
%if (NUM_WORDS < 1) || (NUM_WORDS > 64)
%fatal <num_words_IS_INCORRECT>
%endif
NUM_SKIP_BYTES equ ((NUM_WORDS - 2) * 4)
%define NUM_SKIP_BYTES ((NUM_WORDS - 2) * 4)
MOVZXLO macro dest:req, src:req
movzx dest, @CatStr(src, _L)
endm
MOVZXHI macro dest:req, src:req
movzx dest, @CatStr(src, _H)
endm
; ALIGN_MASK is 3 or 7 bytes alignment:
%define ALIGN_MASK (7 - (NUM_WORDS & 1) * 4)
ifdef x64
%macro CRC_1 5 ; op, dest, src, t, word_index
%assign n %find(%3, x0,x1,x2,x3,x4,x5,x6,x7)
%if n == 0
%fatal <CRC_1_src_param_IS_INCORRECT>
%else
; x<n> ==> x<n>_R
%1 %2, [rT + %tok(%strcat('x', %eval(n-1), "_R")) * 8 + 0800h * (%4) + (%5) * 4]
%endif
%endmacro
rD equ r11
rN equ r10
rT equ r9
CRC_OP macro op:req, dest:req, src:req, t:req
op dest, QWORD PTR [rT + @CatStr(src, _R) * 8 + 0800h * (t)]
endm
CRC_XOR macro dest:req, src:req, t:req
CRC_OP xor, dest, src, t
endm
CRC_MOV macro dest:req, src:req, t:req
CRC_OP mov, dest, src, t
endm
%if XBITS == 64
CRC1b macro
movzx x6, BYTE PTR [rD]
%define rD r11
%define rN r10
%define rT r9
%macro CRC_OP 4
CRC_1 %1, %2, %3, %4, 0
%endmacro
%macro CRC_XOR 3 ; dest, src, t
CRC_OP xor, %1, %2, %3
%endmacro
%macro CRC_MOV 3 ; dest, src, t
CRC_OP mov, %1, %2, %3
%endmacro
%macro CRC1b 0
movzx x6, byte [rD]
inc rD
MOVZXLO x3, x0
xor x6, x3
shr r0, 8
CRC_XOR r0, x6, 0
dec rN
endm
%endmacro
; ALIGN_MASK is 3 or 7 bytes alignment:
ALIGN_MASK equ (7 - (NUM_WORDS and 1) * 4)
%if NUM_WORDS == 1
if NUM_WORDS eq 1
src_rN_offset equ 4
%define src_rN_offset 4
; + 4 for prefetching next 4-bytes after current iteration
NUM_BYTES_LIMIT equ (NUM_WORDS * 4 + 4)
SRCDAT4 equ DWORD PTR [rN + rD * 1]
%define NUM_BYTES_LIMIT (NUM_WORDS * 4 + 4)
%define SRCDAT4 DWORD [rN + rD * 1]
XOR_NEXT macro
%macro XOR_NEXT 0
mov x1, [rD]
xor r0, r1
endm
%endmacro
else ; NUM_WORDS > 1
%else ; NUM_WORDS > 1
src_rN_offset equ 8
%define src_rN_offset 8
; + 8 for prefetching next 8-bytes after current iteration
NUM_BYTES_LIMIT equ (NUM_WORDS * 4 + 8)
%define NUM_BYTES_LIMIT (NUM_WORDS * 4 + 8)
XOR_NEXT macro
xor r0, QWORD PTR [rD] ; 64-bit read, can be unaligned
endm
%macro XOR_NEXT 0
xor r0, QWORD [rD] ; 64-bit read, can be unaligned
%endmacro
; 32-bit or 64-bit
LOAD_SRC_MULT4 macro dest:req, word_index:req
mov dest, [rN + rD * 1 + 4 * (word_index) - src_rN_offset];
endm
%macro LOAD_SRC_MULT4 2 ; dest, word_index
mov %1, [rN + rD * 1 + 4 * (%2) - src_rN_offset];
%endmacro
endif
%endif
MY_PROC @CatStr(XzCrc64UpdateT, %(NUM_WORDS * 4)), 4
MY_PROC AddNum(XzCrc64UpdateT, NUM_WORDS * 4), 4
MY_PUSH_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
mov r0, REG_ABI_PARAM_0 ; r0 <- r1 / r7
mov rD, REG_ABI_PARAM_1 ; r11 <- r2 / r6
mov rN, REG_ABI_PARAM_2 ; r10 <- r8 / r2
if (IS_LINUX gt 0)
%if ABI == LINUX
mov rT, REG_ABI_PARAM_3 ; r9 <- r9 / r1
endif
%endif
cmp rN, NUM_BYTES_LIMIT + ALIGN_MASK
jb crc_end
jb .crc_end
@@:
test rD, ALIGN_MASK
jz @F
@ -109,10 +112,10 @@ endif
sub rD, rN
add rN, src_rN_offset
align 16
ALIGN 16
@@:
if NUM_WORDS eq 1
%if NUM_WORDS == 1
mov x1, x0
shr x1, 8
@ -128,28 +131,33 @@ if NUM_WORDS eq 1
CRC_XOR r0, x2, 1
CRC_XOR r0, x1, 0
else ; NUM_WORDS > 1
if NUM_WORDS ne 2
k = 2
while k lt NUM_WORDS
%else ; NUM_WORDS > 1
%if NUM_WORDS != 2
%assign k 2
%rep NUM_WORDS
%if k == NUM_WORDS
%exitrep
%endif
LOAD_SRC_MULT4 x1, k
crc_op1 textequ <xor>
%define crc_op1 xor
if k eq 2
if (NUM_WORDS and 1)
%if k == 2
%if (NUM_WORDS & 1)
LOAD_SRC_MULT4 x7, NUM_WORDS ; aligned 32-bit
LOAD_SRC_MULT4 x6, NUM_WORDS + 1 ; aligned 32-bit
shl r6, 32
else
%else
LOAD_SRC_MULT4 r6, NUM_WORDS ; aligned 64-bit
crc_op1 textequ <mov>
endif
endif
table = 4 * (NUM_WORDS - 1 - k)
%undef crc_op1
%define crc_op1 mov
%endif
%endif
%assign table (4 * (NUM_WORDS - 1 - k))
MOVZXLO x3, x1
CRC_OP crc_op1, r7, x3, 3 + table
CRC_OP crc_op1, r7, x3, 3 + table
MOVZXHI x3, x1
shr x1, 16
CRC_XOR r6, x3, 2 + table
@ -157,14 +165,14 @@ if NUM_WORDS ne 2
shr x1, 8
CRC_XOR r7, x3, 1 + table
CRC_XOR r6, x1, 0 + table
k = k + 1
endm
crc_op2 textequ <xor>
%assign k k+1
%endrep
%define crc_op2 xor
else ; NUM_WORDS == 2
LOAD_SRC_MULT4 r6, NUM_WORDS ; aligned 64-bit
crc_op2 textequ <mov>
endif ; NUM_WORDS == 2
%else ; NUM_WORDS == 2
LOAD_SRC_MULT4 r6, NUM_WORDS ; aligned 64-bit
%define crc_op2 mov
%endif ; NUM_WORDS == 2
MOVZXHI x3, x0
MOVZXLO x2, x0
@ -189,7 +197,7 @@ endif ; NUM_WORDS == 2
xor r0, r6
xor r0, r7
endif ; NUM_WORDS > 1
%endif ; NUM_WORDS > 1
add rD, NUM_WORDS * 4
jnc @B
@ -199,78 +207,73 @@ endif ; NUM_WORDS > 1
add rN, NUM_BYTES_LIMIT - 1
sub rN, rD
crc_end:
.crc_end:
test rN, rN
jz func_end
jz .func_end
@@:
CRC1b
jnz @B
func_end:
jnz @B
.func_end:
MY_POP_PRESERVED_ABI_REGS_UP_TO_INCLUDING_R11
MY_ENDP
MY_ENDP
else
%else
; ==================================================================
; x86 (32-bit)
rD equ r7
rN equ r1
rT equ r5
%define rD r7
%define rN r1
%define rT r5
xA equ x6
xA_R equ r6
%define xA x6
%define xA_R r6
ifdef x64
num_VAR equ r8
else
%if XBITS == 64
%define num_VAR r8
%else
%define crc_OFFS (REG_SIZE * 5)
crc_OFFS equ (REG_SIZE * 5)
if (IS_CDECL gt 0) or (IS_LINUX gt 0)
%if (IS_CDECL == 1) || (ABI == LINUX)
; cdecl or (GNU fastcall) stack:
; (UInt32 *) table
; size_t size
; void * data
; (UInt64) crc
; ret-ip <-(r4)
data_OFFS equ (8 + crc_OFFS)
size_OFFS equ (REG_SIZE + data_OFFS)
table_OFFS equ (REG_SIZE + size_OFFS)
num_VAR equ [r4 + size_OFFS]
table_VAR equ [r4 + table_OFFS]
else
%define data_OFFS (8 + crc_OFFS)
%define size_OFFS (REG_SIZE + data_OFFS)
%define table_OFFS (REG_SIZE + size_OFFS)
%define num_VAR [r4 + size_OFFS]
%define table_VAR [r4 + table_OFFS]
%else
; Windows fastcall:
; r1 = data, r2 = size
; stack:
; (UInt32 *) table
; (UInt64) crc
; ret-ip <-(r4)
table_OFFS equ (8 + crc_OFFS)
table_VAR equ [r4 + table_OFFS]
num_VAR equ table_VAR
endif
endif ; x64
%define table_OFFS (8 + crc_OFFS)
%define table_VAR [r4 + table_OFFS]
%define num_VAR table_VAR
%endif
%endif
SRCDAT4 equ DWORD PTR [rN + rD * 1]
%define SRCDAT4 DWORD [rN + rD * 1]
CRC_1 macro op:req, dest:req, src:req, t:req, word_index:req
op dest, DWORD PTR [rT + @CatStr(src, _R) * 8 + 0800h * (t) + (word_index) * 4]
endm
%macro CRC 6 ; op0, op1, dest0, dest1, src, t
CRC_1 %1, %3, %5, %6, 0
CRC_1 %2, %4, %5, %6, 1
%endmacro
CRC macro op0:req, op1:req, dest0:req, dest1:req, src:req, t:req
CRC_1 op0, dest0, src, t, 0
CRC_1 op1, dest1, src, t, 1
endm
CRC_XOR macro dest0:req, dest1:req, src:req, t:req
CRC xor, xor, dest0, dest1, src, t
endm
%macro CRC_XOR 4 ; dest0, dest1, src, t
CRC xor, xor, %1, %2, %3, %4
%endmacro
CRC1b macro
movzx xA, BYTE PTR [rD]
%macro CRC1b 0
movzx xA, BYTE [rD]
inc rD
MOVZXLO x3, x0
xor xA, x3
@ -278,12 +281,12 @@ CRC1b macro
shr x2, 8
CRC_XOR x0, x2, xA, 0
dec rN
endm
%endmacro
MY_PROLOG_BASE macro
%macro MY_PROLOG_BASE 0
MY_PUSH_4_REGS
ifdef x64
%if XBITS == 64
mov r0, REG_ABI_PARAM_0 ; r0 <- r1 / r7
mov rT, REG_ABI_PARAM_3 ; r5 <- r9 / r1
mov rN, REG_ABI_PARAM_2 ; r1 <- r8 / r2
@ -291,50 +294,47 @@ ifdef x64
mov r2, r0
shr r2, 32
mov x0, x0
else
if (IS_CDECL gt 0) or (IS_LINUX gt 0)
proc_numParams = proc_numParams + 2 ; for ABI_LINUX
%else
%if (IS_CDECL == 1) || (ABI == LINUX)
%assign proc_numParams proc_numParams + 2 ; for ABI_LINUX
mov rN, [r4 + size_OFFS]
mov rD, [r4 + data_OFFS]
else
%else
mov rD, REG_ABI_PARAM_0 ; r7 <- r1 : (data)
mov rN, REG_ABI_PARAM_1 ; r1 <- r2 : (size)
endif
%endif
mov x0, [r4 + crc_OFFS]
mov x2, [r4 + crc_OFFS + 4]
mov rT, table_VAR
endif
endm
%endif
%endmacro
MY_EPILOG_BASE macro crc_end:req, func_end:req
crc_end:
%macro MY_EPILOG_BASE 0
.crc_end:
test rN, rN
jz func_end
jz %%func_end
@@:
CRC1b
jnz @B
func_end:
ifdef x64
jnz @B
%%func_end:
%if XBITS == 64
shl r2, 32
xor r0, r2
endif
%endif
MY_POP_4_REGS
endm
%endmacro
; ALIGN_MASK is 3 or 7 bytes alignment:
ALIGN_MASK equ (7 - (NUM_WORDS and 1) * 4)
%if NUM_WORDS == 1
if (NUM_WORDS eq 1)
%define NUM_BYTES_LIMIT_T4 (NUM_WORDS * 4 + 4)
NUM_BYTES_LIMIT_T4 equ (NUM_WORDS * 4 + 4)
MY_PROC @CatStr(XzCrc64UpdateT, %(NUM_WORDS * 4)), 5
MY_PROC AddNum(XzCrc64UpdateT, NUM_WORDS * 4), 5
MY_PROLOG_BASE
cmp rN, NUM_BYTES_LIMIT_T4 + ALIGN_MASK
jb crc_end_4
jb .crc_end
@@:
test rD, ALIGN_MASK
jz @F
@ -347,7 +347,7 @@ MY_PROC @CatStr(XzCrc64UpdateT, %(NUM_WORDS * 4)), 5
add rN, 4
MOVZXLO xA, x0
align 16
ALIGN 16
@@:
mov x3, SRCDAT4
xor x3, x2
@ -374,108 +374,103 @@ align 16
xor x0, [rD]
add rN, NUM_BYTES_LIMIT_T4 - 1
sub rN, rD
MY_EPILOG_BASE crc_end_4, func_end_4
MY_ENDP
else ; NUM_WORDS > 1
MY_EPILOG_BASE
MY_ENDP
SHR_X macro x, imm
shr x, imm
endm
%else ; NUM_WORDS > 1
ITER_1 macro v0, v1, a, off
MOVZXLO xA, a
SHR_X a, 8
CRC_XOR v0, v1, xA, off
endm
%macro ITER_1 4
MOVZXLO xA, %3
shr %3, 8
CRC_XOR %1, %2, xA, %4
%endmacro
ITER_4 macro v0, v1, a, off
if 0 eq 0
ITER_1 v0, v1, a, off + 3
ITER_1 v0, v1, a, off + 2
ITER_1 v0, v1, a, off + 1
CRC_XOR v0, v1, a, off
elseif 0 eq 0
MOVZXLO xA, a
CRC_XOR v0, v1, xA, off + 3
mov xA, a
ror a, 16 ; 32-bit ror
%macro ITER_4 4 ; v0, v1, a, off
%if 0 == 0
ITER_1 %1, %2, %3, %4 + 3
ITER_1 %1, %2, %3, %4 + 2
ITER_1 %1, %2, %3, %4 + 1
CRC_XOR %1, %2, %3, %4
%elif 0 == 0
MOVZXLO xA, %3
CRC_XOR %1, %2, xA, %4 + 3
mov xA, %3
ror %3, 16 ; 32-bit ror
shr xA, 24
CRC_XOR v0, v1, xA, off
MOVZXLO xA, a
SHR_X a, 24
CRC_XOR v0, v1, xA, off + 1
CRC_XOR v0, v1, a, off + 2
else
CRC_XOR %1, %2, xA, %4
movzx xA, %3
shr %3, 24
CRC_XOR %1, %2, xA, %4 + 1
CRC_XOR %1, %2, %3, %4 + 2
%else
; MOVZXHI provides smaller code, but MOVZX_HI_BYTE is not fast instruction
MOVZXLO xA, a
CRC_XOR v0, v1, xA, off + 3
MOVZXHI xA, a
SHR_X a, 16
CRC_XOR v0, v1, xA, off + 2
MOVZXLO xA, a
SHR_X a, 8
CRC_XOR v0, v1, xA, off + 1
CRC_XOR v0, v1, a, off
endif
endm
MOVZXLO xA, %3
CRC_XOR %1, %2, xA, %4 + 3
MOVZXHI xA, %3
shr %3, 16
CRC_XOR %1, %2, xA, %4 + 2
MOVZXLO xA, %3
shr %3, 8
CRC_XOR %1, %2, xA, %4 + 1
CRC_XOR %1, %2, %3, %4
%endif
%endmacro
%macro ITER_1_PAIR 5 ; v0, v1, a0, a1, off
ITER_1 %1, %2, %3, %5 + 4
ITER_1 %1, %2, %4, %5
%endmacro
ITER_1_PAIR macro v0, v1, a0, a1, off
ITER_1 v0, v1, a0, off + 4
ITER_1 v0, v1, a1, off
endm
%define src_rD_offset 8
%define STEP_SIZE (NUM_WORDS * 4)
src_rD_offset equ 8
STEP_SIZE equ (NUM_WORDS * 4)
%macro ITER_12_NEXT 4 ; op, index, v0, v1
%1 %3, DWORD [rD + (%2 + 1) * STEP_SIZE - src_rD_offset]
%1 %4, DWORD [rD + (%2 + 1) * STEP_SIZE + 4 - src_rD_offset]
%endmacro
ITER_12_NEXT macro op, index, v0, v1
op v0, DWORD PTR [rD + (index + 1) * STEP_SIZE - src_rD_offset]
op v1, DWORD PTR [rD + (index + 1) * STEP_SIZE + 4 - src_rD_offset]
endm
%macro ITER_12 5 ; index, a0, a1, v0, v1
%if NUM_SKIP_BYTES == 0
ITER_12_NEXT mov, %1, %4, %5
%else
%assign k 0
%rep NUM_SKIP_BYTES
movzx xA, BYTE [rD + %1 * STEP_SIZE + k + 8 - src_rD_offset]
%if k == 0
CRC mov, mov, %4, %5, xA, NUM_SKIP_BYTES - 1 - k
%else
CRC_XOR %4, %5, xA, NUM_SKIP_BYTES - 1 - k
%endif
%assign k k+1
%endrep
ITER_12_NEXT xor, %1, %4, %5
%endif
ITER_12 macro index, a0, a1, v0, v1
if NUM_SKIP_BYTES eq 0
ITER_12_NEXT mov, index, v0, v1
else
k = 0
while k lt NUM_SKIP_BYTES
movzx xA, BYTE PTR [rD + (index) * STEP_SIZE + k + 8 - src_rD_offset]
if k eq 0
CRC mov, mov, v0, v1, xA, NUM_SKIP_BYTES - 1 - k
else
CRC_XOR v0, v1, xA, NUM_SKIP_BYTES - 1 - k
endif
k = k + 1
endm
ITER_12_NEXT xor, index, v0, v1
endif
if 0 eq 0
ITER_4 v0, v1, a0, NUM_SKIP_BYTES + 4
ITER_4 v0, v1, a1, NUM_SKIP_BYTES
else ; interleave version is faster/slower for different processors
ITER_1_PAIR v0, v1, a0, a1, NUM_SKIP_BYTES + 3
ITER_1_PAIR v0, v1, a0, a1, NUM_SKIP_BYTES + 2
ITER_1_PAIR v0, v1, a0, a1, NUM_SKIP_BYTES + 1
CRC_XOR v0, v1, a0, NUM_SKIP_BYTES + 4
CRC_XOR v0, v1, a1, NUM_SKIP_BYTES
endif
endm
%if 0 == 0
ITER_4 %4, %5, %2, NUM_SKIP_BYTES + 4
ITER_4 %4, %5, %3, NUM_SKIP_BYTES
%else ; interleave version is faster/slower for different processors
ITER_1_PAIR %4, %5, %2, %3, NUM_SKIP_BYTES + 3
ITER_1_PAIR %4, %5, %2, %3, NUM_SKIP_BYTES + 2
ITER_1_PAIR %4, %5, %2, %3, NUM_SKIP_BYTES + 1
CRC_XOR %4, %5, %2, NUM_SKIP_BYTES + 4
CRC_XOR %4, %5, %3, NUM_SKIP_BYTES
%endif
%endmacro
; we use (UNROLL_CNT > 1) to reduce read ports pressure (num_VAR reads)
UNROLL_CNT equ (2 * 1)
NUM_BYTES_LIMIT equ (STEP_SIZE * UNROLL_CNT + 8)
%define UNROLL_CNT (2 * 1)
%define NUM_BYTES_LIMIT (STEP_SIZE * UNROLL_CNT + 8)
MY_PROC @CatStr(XzCrc64UpdateT, %(NUM_WORDS * 4)), 5
MY_PROC AddNum(XzCrc64UpdateT, NUM_WORDS * 4), 5
MY_PROLOG_BASE
cmp rN, NUM_BYTES_LIMIT + ALIGN_MASK
jb crc_end_12
jb .crc_end
@@:
test rD, ALIGN_MASK
jz @F
@ -488,22 +483,22 @@ MY_PROC @CatStr(XzCrc64UpdateT, %(NUM_WORDS * 4)), 5
lea rN, [rD + rN * 1 - (NUM_BYTES_LIMIT - 1)]
mov num_VAR, rN
align 16
ALIGN 16
@@:
i = 0
rept UNROLL_CNT
if (i and 1) eq 0
ITER_12 i, x0, x2, x1, x3
else
ITER_12 i, x1, x3, x0, x2
endif
i = i + 1
endm
%assign i 0
%rep UNROLL_CNT
%if (i & 1) == 0
ITER_12 i, x0, x2, x1, x3
%else
ITER_12 i, x1, x3, x0, x2
%endif
%assign i i+1
%endrep
if (UNROLL_CNT and 1)
%if (UNROLL_CNT & 1)
mov x0, x1
mov x2, x3
endif
%endif
add rD, STEP_SIZE * UNROLL_CNT
cmp rD, num_VAR
jb @B
@ -515,9 +510,9 @@ align 16
xor x0, [rD]
xor x2, [rD + 4]
MY_EPILOG_BASE crc_end_12, func_end_12
MY_ENDP
MY_EPILOG_BASE
MY_ENDP
%endif ; (NUM_WORDS > 1)
%endif ; ! x64
endif ; (NUM_WORDS > 1)
endif ; ! x64
end

View file

@ -1,8 +1,7 @@
MY_ARCH_2 = $(MY_ARCH)
MY_ASM = jwasm
MY_ASM = asmc
MY_ASM = nasm
ifndef RC
#RC=windres.exe --target=pe-x86-64
@ -129,14 +128,12 @@ endif
ifdef IS_X64
AFLAGS_ABI = -elf64 -DABI_LINUX
AFLAGS_ABI = -felf64
else
AFLAGS_ABI = -elf -DABI_LINUX -DABI_CDECL
# -DABI_CDECL
# -DABI_LINUX
# -DABI_CDECL
AFLAGS_ABI = -felf32
endif
AFLAGS = $(AFLAGS_ABI) -Fo$(O)/
AFLAGS = $(AFLAGS_ABI) -I$(<D) -o $(O)/$(*F).o
C_WARN_FLAGS =
@ -148,7 +145,10 @@ STATIC_TARGET=$(PROGPATH_STATIC)
endif
all: $(O) $(PROGPATH) $(STATIC_TARGET)
all: $(PROGPATH) $(STATIC_TARGET)
# we need $(O) as order-only-prerequisites:
$(OBJS): | $(O)
$(O):
$(MY_MKDIR) $(O)

View file

@ -7,10 +7,8 @@
MY_ARCH_2 = $(MY_ARCH)
MY_ASM = asmc
ifdef USE_JWASM
MY_ASM = jwasm
endif
MY_ASM = nasm
ifndef RC
RC=windres.exe --target=pe-x86-64
@ -175,29 +173,23 @@ CFLAGS = $(MY_ARCH_2) $(LOCAL_FLAGS) $(CFLAGS_BASE2) $(CFLAGS_BASE) $(FLAGS_FLTO
ifdef IS_MINGW
ifdef IS_X64
AFLAGS_ABI = -win64
AFLAGS_ABI = -fwin64
else
AFLAGS_ABI = -coff -DABI_CDECL
# -DABI_CDECL
# -DABI_LINUX
# -DABI_CDECL
AFLAGS_ABI = -fwin32 -DABI_CDECL
endif
AFLAGS = -nologo $(AFLAGS_ABI) -Fo$(O)/$(basename $(<F)).o
else # IS_MINGW
ifdef IS_X64
AFLAGS_ABI = -elf64 -DABI_LINUX
AFLAGS_ABI = -felf64
else
AFLAGS_ABI = -elf -DABI_LINUX -DABI_CDECL
# -DABI_CDECL
# -DABI_LINUX
# -DABI_CDECL
AFLAGS_ABI = -felf32
endif
AFLAGS = -nologo $(AFLAGS_ABI) -Fo$(O)/
endif # IS_MINGW
AFLAGS = $(AFLAGS_ABI) -I$(<D) -o $(O)/$(*F).o
ifdef USE_ASM
@ -1286,9 +1278,7 @@ $O/Sha256Opt.o: ../../../../Asm/x86/Sha256Opt.asm
$O/Sort.o: ../../../../Asm/x86/Sort.asm
$(MY_ASM) $(AFLAGS) $<
ifndef USE_JWASM
USE_X86_ASM_AES=1
endif
else
$O/7zCrcOpt.o: ../../../../C/7zCrcOpt.c

View file

@ -1,3 +1,9 @@
ifneq ($(shell $(CC) -dumpmachine 2>/dev/null | grep 'x86_64'), )
IS_X64 = 1
endif
USE_ASM = 1
ifdef USE_ASM
ifdef IS_X64
USE_LZMA_DEC_ASM=1

View file

@ -26,14 +26,16 @@ O=o
!IF "$(PLATFORM)" == "x64"
MY_ML = ml64 -WX
MY_ML = nasm -fwin64
#MY_ML = ml64 -WX
#-Dx64
!ELSEIF "$(PLATFORM)" == "arm64"
MY_ML = armasm64
!ELSEIF "$(PLATFORM)" == "arm"
MY_ML = armasm -WX
!ELSE
MY_ML = ml -WX
MY_ML = nasm -fwin32
#MY_ML = ml -WX
# -DABI_CDECL
!ENDIF
@ -60,7 +62,8 @@ COMPL_ASM = $(MY_ML) $** $O/$(*B).obj
!ELSEIF "$(PLATFORM)" == "arm64"
COMPL_ASM = $(MY_ML) $** $O/$(*B).obj
!ELSE
COMPL_ASM = $(MY_ML) -c -Fo$O/ $**
#COMPL_ASM = $(MY_ML) -c -Fo$O/ $**
COMPL_ASM = $(MY_ML) -I$(*D) -o $O/$(*B).obj $**
!ENDIF
!IFDEF OLD_COMPILER