Jump to content
mikerabat

Fast Base64 encode/decode

Recommended Posts

I just released an assembler optimzed (AVX2 set) Base64 encoding/decoding unit.

 

check it out under
https://github.com/mikerabat/fastbase64/

 

My reference implementation achieves up to 10 times speedup against the reference Indy implementation.

Let me know what you think or if you encounter some errors...

  • Like 2
  • Thanks 2

Share this post


Link to post
21 minutes ago, mikerabat said:

Let me know what you think or if you encounter some errors...

Personally, I would find it way more readable if you would not ifdef DELPHIAVX for every single line but simply make it two blocks, one using the avx instructions and one using db.

  • Like 2
  • Thanks 1

Share this post


Link to post

Jus FYI: That is intentional - the left side shall show the original assembler call the right side the DB translation

-> my tool, that derrives the DB statements from the assembler code does a line by line comparison.

 

Share this post


Link to post
2 hours ago, mikerabat said:

Jus FYI: That is intentional - the left side shall show the original assembler call the right side the DB translation

Maybe at least reformat it into two distinct columns

      {$IFDEF DELPHIAVX}vpshufb ymm1, ymm0, [r9 + TAVXEncodeConst.Lut0];{$ELSE}db $C4,$C2,$7D,$00,$49,$20;{$ENDIF}
      {$IFDEF DELPHIAVX}vpand ymm2, ymm1, [r9 + TAVXEncodeConst.Mask0];{$ELSE}db $C4,$C1,$75,$DB,$51,$60;{$ENDIF}
      {$IFDEF DELPHIAVX}vpand ymm1, ymm1, [r9 + TAVXEncodeConst.Mask2];{$ELSE}db $C4,$C1,$75,$DB,$89,$A0,$00,$00,$00;{$ENDIF}
      {$IFDEF DELPHIAVX}vpmulhuw ymm2, ymm2, [r9 + TAVXEncodeConst.Mask1];{$ELSE}db $C4,$C1,$6D,$E4,$91,$80,$00,$00,$00;{$ENDIF}
      {$IFDEF DELPHIAVX}vpmullw ymm1, ymm1, [r9 + TAVXEncodeConst.Mask3];{$ELSE}db $C4,$C1,$75,$D5,$89,$C0,$00,$00,$00;{$ENDIF}
      {$IFDEF DELPHIAVX}vpor ymm1, ymm1, ymm2;{$ELSE}db $C5,$F5,$EB,$CA;{$ENDIF}

Like this:

{$IFDEF DELPHIAVX}      vpshufb ymm1, ymm0, [r9 + TAVXEncodeConst.Lut0];                {$ELSE}db $C4,$C2,$7D,$00,$49,$20;{$ENDIF}
{$IFDEF DELPHIAVX}      vpand ymm2, ymm1, [r9 + TAVXEncodeConst.Mask0];			{$ELSE}db $C4,$C1,$75,$DB,$51,$60;{$ENDIF}
{$IFDEF DELPHIAVX}      vpand ymm1, ymm1, [r9 + TAVXEncodeConst.Mask2];			{$ELSE}db $C4,$C1,$75,$DB,$89,$A0,$00,$00,$00;{$ENDIF}
{$IFDEF DELPHIAVX}      vpmulhuw ymm2, ymm2, [r9 + TAVXEncodeConst.Mask1];		{$ELSE}db $C4,$C1,$6D,$E4,$91,$80,$00,$00,$00;{$ENDIF}
{$IFDEF DELPHIAVX}      vpmullw ymm1, ymm1, [r9 + TAVXEncodeConst.Mask3];		{$ELSE}db $C4,$C1,$75,$D5,$89,$C0,$00,$00,$00;{$ENDIF}
{$IFDEF DELPHIAVX}      vpor ymm1, ymm1, ymm2;						{$ELSE}db $C5,$F5,$EB,$CA;{$ENDIF}

or even better:

{$IFDEF DELPHIAVX}      vpshufb         ymm1, ymm0, [r9 + TAVXEncodeConst.Lut0];                {$ELSE}db $C4,$C2,$7D,$00,$49,$20;{$ENDIF}
{$IFDEF DELPHIAVX}      vpand           ymm2, ymm1, [r9 + TAVXEncodeConst.Mask0];		{$ELSE}db $C4,$C1,$75,$DB,$51,$60;{$ENDIF}
{$IFDEF DELPHIAVX}      vpand           ymm1, ymm1, [r9 + TAVXEncodeConst.Mask2];		{$ELSE}db $C4,$C1,$75,$DB,$89,$A0,$00,$00,$00;{$ENDIF}
{$IFDEF DELPHIAVX}      vpmulhuw        ymm2, ymm2, [r9 + TAVXEncodeConst.Mask1];		{$ELSE}db $C4,$C1,$6D,$E4,$91,$80,$00,$00,$00;{$ENDIF}
{$IFDEF DELPHIAVX}      vpmullw         ymm1, ymm1, [r9 + TAVXEncodeConst.Mask3];		{$ELSE}db $C4,$C1,$75,$D5,$89,$C0,$00,$00,$00;{$ENDIF}
{$IFDEF DELPHIAVX}      vpor            ymm1, ymm1, ymm2;					{$ELSE}db $C5,$F5,$EB,$CA;{$ENDIF}

 

Unreadable code is unmaintainable.

  • Like 4

Share this post


Link to post
2 hours ago, mikerabat said:

Jus FYI: That is intentional - the left side shall show the original assembler call the right side the DB translation

-> my tool, that derrives the DB statements from the assembler code does a line by line comparison.

 

I think I'd extend the tool to produce cleaner output

Share this post


Link to post

Thanks for the input - I will beef up the tool to get at least the else part aligned on the right side 😉  that really looks nicer.

Share this post


Link to post
3 hours ago, mikerabat said:

Thanks for the input - I will beef up the tool to get at least the else part aligned on the right side 😉  that really looks nicer.

One thing you could easily do would be to always output the db instructions, but put the asm in comments, then it would be just as readable, but have no ifdefs

Share this post


Link to post
18 minutes ago, David Heffernan said:

One thing you could easily do would be to always output the db instructions, but put the asm in comments, then it would be just as readable, but have no ifdefs

...and no errors from the compiler if the asm is wrong.

Share this post


Link to post

@David Heffernan That would be against the direction I develop here - first I need the working ASM 😉 then the tool can use the disassembly to create the db instructions....

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×