-module(packkit@internal@aes).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/packkit/internal/aes.gleam").
-export([encrypt_block/2, decrypt_block/2, expand_key/1]).
-export_type([expanded_key/0]).
-if(?OTP_RELEASE >= 27).
-define(MODULEDOC(Str), -moduledoc(Str)).
-define(DOC(Str), -doc(Str)).
-else.
-define(MODULEDOC(Str), -compile([])).
-define(DOC(Str), -compile([])).
-endif.
?MODULEDOC(false).
-opaque expanded_key() :: {expanded_key, list(integer()), integer()}.
-file("src/packkit/internal/aes.gleam", 113).
?DOC(false).
-spec rcon_byte(integer()) -> integer().
rcon_byte(Round) ->
case Round of
1 ->
16#01;
2 ->
16#02;
3 ->
16#04;
4 ->
16#08;
5 ->
16#10;
6 ->
16#20;
7 ->
16#40;
8 ->
16#80;
9 ->
16#1B;
10 ->
16#36;
_ ->
16#00
end.
-file("src/packkit/internal/aes.gleam", 108).
?DOC(false).
-spec rcon_value(integer()) -> integer().
rcon_value(Round) ->
Rc = rcon_byte(Round),
erlang:'bsl'(Rc, 24).
-file("src/packkit/internal/aes.gleam", 178).
?DOC(false).
-spec xor_word_lists(list(integer()), list(integer()), list(integer())) -> list(integer()).
xor_word_lists(A, B, Acc) ->
case {A, B} of
{[], _} ->
lists:reverse(Acc);
{_, []} ->
lists:reverse(Acc);
{[X | Rest_a], [Y | Rest_b]} ->
xor_word_lists(Rest_a, Rest_b, [erlang:'bxor'(X, Y) | Acc])
end.
-file("src/packkit/internal/aes.gleam", 169).
?DOC(false).
-spec add_round_key(list(integer()), list(integer()), integer()) -> list(integer()).
add_round_key(State, Round_keys, Round) ->
Key_slice = gleam@list:take(gleam@list:drop(Round_keys, Round * 4), 4),
xor_word_lists(State, Key_slice, []).
-file("src/packkit/internal/aes.gleam", 236).
?DOC(false).
-spec mix_xor4(integer(), integer(), integer(), integer()) -> integer().
mix_xor4(A, B, C, D) ->
erlang:'bxor'(erlang:'bxor'(A, B), erlang:'bxor'(C, D)).
-file("src/packkit/internal/aes.gleam", 245).
?DOC(false).
-spec gmul2(integer()) -> integer().
gmul2(Value) ->
Shifted = erlang:'band'(erlang:'bsl'(Value, 1), 16#FF),
case erlang:'band'(Value, 16#80) of
0 ->
Shifted;
_ ->
erlang:'bxor'(Shifted, 16#1B)
end.
-file("src/packkit/internal/aes.gleam", 253).
?DOC(false).
-spec gmul3(integer()) -> integer().
gmul3(Value) ->
erlang:'bxor'(gmul2(Value), Value).
-file("src/packkit/internal/aes.gleam", 215).
?DOC(false).
-spec mix_one_column(integer()) -> integer().
mix_one_column(Word) ->
S0 = erlang:'band'(erlang:'bsr'(Word, 24), 16#FF),
S1 = erlang:'band'(erlang:'bsr'(Word, 16), 16#FF),
S2 = erlang:'band'(erlang:'bsr'(Word, 8), 16#FF),
S3 = erlang:'band'(Word, 16#FF),
R0 = mix_xor4(gmul2(S0), gmul3(S1), S2, S3),
R1 = mix_xor4(S0, gmul2(S1), gmul3(S2), S3),
R2 = mix_xor4(S0, S1, gmul2(S2), gmul3(S3)),
R3 = mix_xor4(gmul3(S0), S1, S2, gmul2(S3)),
erlang:'bor'(
erlang:'bor'(
erlang:'bor'(erlang:'bsl'(R0, 24), erlang:'bsl'(R1, 16)),
erlang:'bsl'(R2, 8)
),
R3
).
-file("src/packkit/internal/aes.gleam", 211).
?DOC(false).
-spec mix_columns(list(integer())) -> list(integer()).
mix_columns(State) ->
gleam@list:map(State, fun mix_one_column/1).
-file("src/packkit/internal/aes.gleam", 361).
?DOC(false).
-spec gmul4(integer()) -> integer().
gmul4(Value) ->
gmul2(gmul2(Value)).
-file("src/packkit/internal/aes.gleam", 365).
?DOC(false).
-spec gmul8(integer()) -> integer().
gmul8(Value) ->
gmul2(gmul4(Value)).
-file("src/packkit/internal/aes.gleam", 369).
?DOC(false).
-spec gmul9(integer()) -> integer().
gmul9(Value) ->
erlang:'bxor'(gmul8(Value), Value).
-file("src/packkit/internal/aes.gleam", 373).
?DOC(false).
-spec gmul11(integer()) -> integer().
gmul11(Value) ->
erlang:'bxor'(erlang:'bxor'(gmul8(Value), gmul2(Value)), Value).
-file("src/packkit/internal/aes.gleam", 380).
?DOC(false).
-spec gmul13(integer()) -> integer().
gmul13(Value) ->
erlang:'bxor'(erlang:'bxor'(gmul8(Value), gmul4(Value)), Value).
-file("src/packkit/internal/aes.gleam", 387).
?DOC(false).
-spec gmul14(integer()) -> integer().
gmul14(Value) ->
erlang:'bxor'(erlang:'bxor'(gmul8(Value), gmul4(Value)), gmul2(Value)).
-file("src/packkit/internal/aes.gleam", 340).
?DOC(false).
-spec inv_mix_one_column(integer()) -> integer().
inv_mix_one_column(Word) ->
S0 = erlang:'band'(erlang:'bsr'(Word, 24), 16#FF),
S1 = erlang:'band'(erlang:'bsr'(Word, 16), 16#FF),
S2 = erlang:'band'(erlang:'bsr'(Word, 8), 16#FF),
S3 = erlang:'band'(Word, 16#FF),
R0 = mix_xor4(gmul14(S0), gmul11(S1), gmul13(S2), gmul9(S3)),
R1 = mix_xor4(gmul9(S0), gmul14(S1), gmul11(S2), gmul13(S3)),
R2 = mix_xor4(gmul13(S0), gmul9(S1), gmul14(S2), gmul11(S3)),
R3 = mix_xor4(gmul11(S0), gmul13(S1), gmul9(S2), gmul14(S3)),
erlang:'bor'(
erlang:'bor'(
erlang:'bor'(erlang:'bsl'(R0, 24), erlang:'bsl'(R1, 16)),
erlang:'bsl'(R2, 8)
),
R3
).
-file("src/packkit/internal/aes.gleam", 336).
?DOC(false).
-spec inv_mix_columns(list(integer())) -> list(integer()).
inv_mix_columns(State) ->
gleam@list:map(State, fun inv_mix_one_column/1).
-file("src/packkit/internal/aes.gleam", 398).
?DOC(false).
-spec bit_array_to_u32_words(bitstring(), list(integer())) -> list(integer()).
bit_array_to_u32_words(Bytes, Acc) ->
case Bytes of
<<Word:32/big, Rest/binary>> ->
bit_array_to_u32_words(Rest, [Word | Acc]);
_ ->
lists:reverse(Acc)
end.
-file("src/packkit/internal/aes.gleam", 406).
?DOC(false).
-spec u32_words_to_bit_array(list(integer()), bitstring()) -> bitstring().
u32_words_to_bit_array(Words, Acc) ->
case Words of
[] ->
Acc;
[W | Rest] ->
u32_words_to_bit_array(
Rest,
gleam_stdlib:bit_array_concat([Acc, <<W:32/big>>])
)
end.
-file("src/packkit/internal/aes.gleam", 418).
?DOC(false).
-spec words_to_bytes_loop(list(integer()), list(integer())) -> list(integer()).
words_to_bytes_loop(Words, Acc) ->
case Words of
[] ->
lists:reverse(Acc);
[W | Rest] ->
B0 = erlang:'band'(erlang:'bsr'(W, 24), 16#FF),
B1 = erlang:'band'(erlang:'bsr'(W, 16), 16#FF),
B2 = erlang:'band'(erlang:'bsr'(W, 8), 16#FF),
B3 = erlang:'band'(W, 16#FF),
words_to_bytes_loop(Rest, [B3, B2, B1, B0 | Acc])
end.
-file("src/packkit/internal/aes.gleam", 414).
?DOC(false).
-spec words_to_bytes(list(integer())) -> list(integer()).
words_to_bytes(Words) ->
words_to_bytes_loop(Words, []).
-file("src/packkit/internal/aes.gleam", 435).
?DOC(false).
-spec bytes_to_words_loop(list(integer()), list(integer())) -> list(integer()).
bytes_to_words_loop(Bytes, Acc) ->
case Bytes of
[B0, B1, B2, B3 | Rest] ->
Word = erlang:'bor'(
erlang:'bor'(
erlang:'bor'(erlang:'bsl'(B0, 24), erlang:'bsl'(B1, 16)),
erlang:'bsl'(B2, 8)
),
B3
),
bytes_to_words_loop(Rest, [Word | Acc]);
_ ->
lists:reverse(Acc)
end.
-file("src/packkit/internal/aes.gleam", 431).
?DOC(false).
-spec bytes_to_words(list(integer())) -> list(integer()).
bytes_to_words(Bytes) ->
bytes_to_words_loop(Bytes, []).
-file("src/packkit/internal/aes.gleam", 190).
?DOC(false).
-spec shift_rows(list(integer())) -> list(integer()).
shift_rows(State) ->
case words_to_bytes(State) of
[B0, B1, B2, B3, B4, B5, B6, B7, B8, B9, B10, B11, B12, B13, B14, B15] ->
bytes_to_words(
[B0,
B5,
B10,
B15,
B4,
B9,
B14,
B3,
B8,
B13,
B2,
B7,
B12,
B1,
B6,
B11]
);
_ ->
State
end.
-file("src/packkit/internal/aes.gleam", 320).
?DOC(false).
-spec inv_shift_rows(list(integer())) -> list(integer()).
inv_shift_rows(State) ->
case words_to_bytes(State) of
[B0, B1, B2, B3, B4, B5, B6, B7, B8, B9, B10, B11, B12, B13, B14, B15] ->
bytes_to_words(
[B0,
B13,
B10,
B7,
B4,
B1,
B14,
B11,
B8,
B5,
B2,
B15,
B12,
B9,
B6,
B3]
);
_ ->
State
end.
-file("src/packkit/internal/aes.gleam", 457).
?DOC(false).
-spec sbox(integer()) -> integer().
sbox(Byte) ->
case Byte of
16#00 ->
16#63;
16#01 ->
16#7C;
16#02 ->
16#77;
16#03 ->
16#7B;
16#04 ->
16#F2;
16#05 ->
16#6B;
16#06 ->
16#6F;
16#07 ->
16#C5;
16#08 ->
16#30;
16#09 ->
16#01;
16#0A ->
16#67;
16#0B ->
16#2B;
16#0C ->
16#FE;
16#0D ->
16#D7;
16#0E ->
16#AB;
16#0F ->
16#76;
16#10 ->
16#CA;
16#11 ->
16#82;
16#12 ->
16#C9;
16#13 ->
16#7D;
16#14 ->
16#FA;
16#15 ->
16#59;
16#16 ->
16#47;
16#17 ->
16#F0;
16#18 ->
16#AD;
16#19 ->
16#D4;
16#1A ->
16#A2;
16#1B ->
16#AF;
16#1C ->
16#9C;
16#1D ->
16#A4;
16#1E ->
16#72;
16#1F ->
16#C0;
16#20 ->
16#B7;
16#21 ->
16#FD;
16#22 ->
16#93;
16#23 ->
16#26;
16#24 ->
16#36;
16#25 ->
16#3F;
16#26 ->
16#F7;
16#27 ->
16#CC;
16#28 ->
16#34;
16#29 ->
16#A5;
16#2A ->
16#E5;
16#2B ->
16#F1;
16#2C ->
16#71;
16#2D ->
16#D8;
16#2E ->
16#31;
16#2F ->
16#15;
16#30 ->
16#04;
16#31 ->
16#C7;
16#32 ->
16#23;
16#33 ->
16#C3;
16#34 ->
16#18;
16#35 ->
16#96;
16#36 ->
16#05;
16#37 ->
16#9A;
16#38 ->
16#07;
16#39 ->
16#12;
16#3A ->
16#80;
16#3B ->
16#E2;
16#3C ->
16#EB;
16#3D ->
16#27;
16#3E ->
16#B2;
16#3F ->
16#75;
16#40 ->
16#09;
16#41 ->
16#83;
16#42 ->
16#2C;
16#43 ->
16#1A;
16#44 ->
16#1B;
16#45 ->
16#6E;
16#46 ->
16#5A;
16#47 ->
16#A0;
16#48 ->
16#52;
16#49 ->
16#3B;
16#4A ->
16#D6;
16#4B ->
16#B3;
16#4C ->
16#29;
16#4D ->
16#E3;
16#4E ->
16#2F;
16#4F ->
16#84;
16#50 ->
16#53;
16#51 ->
16#D1;
16#52 ->
16#00;
16#53 ->
16#ED;
16#54 ->
16#20;
16#55 ->
16#FC;
16#56 ->
16#B1;
16#57 ->
16#5B;
16#58 ->
16#6A;
16#59 ->
16#CB;
16#5A ->
16#BE;
16#5B ->
16#39;
16#5C ->
16#4A;
16#5D ->
16#4C;
16#5E ->
16#58;
16#5F ->
16#CF;
16#60 ->
16#D0;
16#61 ->
16#EF;
16#62 ->
16#AA;
16#63 ->
16#FB;
16#64 ->
16#43;
16#65 ->
16#4D;
16#66 ->
16#33;
16#67 ->
16#85;
16#68 ->
16#45;
16#69 ->
16#F9;
16#6A ->
16#02;
16#6B ->
16#7F;
16#6C ->
16#50;
16#6D ->
16#3C;
16#6E ->
16#9F;
16#6F ->
16#A8;
16#70 ->
16#51;
16#71 ->
16#A3;
16#72 ->
16#40;
16#73 ->
16#8F;
16#74 ->
16#92;
16#75 ->
16#9D;
16#76 ->
16#38;
16#77 ->
16#F5;
16#78 ->
16#BC;
16#79 ->
16#B6;
16#7A ->
16#DA;
16#7B ->
16#21;
16#7C ->
16#10;
16#7D ->
16#FF;
16#7E ->
16#F3;
16#7F ->
16#D2;
16#80 ->
16#CD;
16#81 ->
16#0C;
16#82 ->
16#13;
16#83 ->
16#EC;
16#84 ->
16#5F;
16#85 ->
16#97;
16#86 ->
16#44;
16#87 ->
16#17;
16#88 ->
16#C4;
16#89 ->
16#A7;
16#8A ->
16#7E;
16#8B ->
16#3D;
16#8C ->
16#64;
16#8D ->
16#5D;
16#8E ->
16#19;
16#8F ->
16#73;
16#90 ->
16#60;
16#91 ->
16#81;
16#92 ->
16#4F;
16#93 ->
16#DC;
16#94 ->
16#22;
16#95 ->
16#2A;
16#96 ->
16#90;
16#97 ->
16#88;
16#98 ->
16#46;
16#99 ->
16#EE;
16#9A ->
16#B8;
16#9B ->
16#14;
16#9C ->
16#DE;
16#9D ->
16#5E;
16#9E ->
16#0B;
16#9F ->
16#DB;
16#A0 ->
16#E0;
16#A1 ->
16#32;
16#A2 ->
16#3A;
16#A3 ->
16#0A;
16#A4 ->
16#49;
16#A5 ->
16#06;
16#A6 ->
16#24;
16#A7 ->
16#5C;
16#A8 ->
16#C2;
16#A9 ->
16#D3;
16#AA ->
16#AC;
16#AB ->
16#62;
16#AC ->
16#91;
16#AD ->
16#95;
16#AE ->
16#E4;
16#AF ->
16#79;
16#B0 ->
16#E7;
16#B1 ->
16#C8;
16#B2 ->
16#37;
16#B3 ->
16#6D;
16#B4 ->
16#8D;
16#B5 ->
16#D5;
16#B6 ->
16#4E;
16#B7 ->
16#A9;
16#B8 ->
16#6C;
16#B9 ->
16#56;
16#BA ->
16#F4;
16#BB ->
16#EA;
16#BC ->
16#65;
16#BD ->
16#7A;
16#BE ->
16#AE;
16#BF ->
16#08;
16#C0 ->
16#BA;
16#C1 ->
16#78;
16#C2 ->
16#25;
16#C3 ->
16#2E;
16#C4 ->
16#1C;
16#C5 ->
16#A6;
16#C6 ->
16#B4;
16#C7 ->
16#C6;
16#C8 ->
16#E8;
16#C9 ->
16#DD;
16#CA ->
16#74;
16#CB ->
16#1F;
16#CC ->
16#4B;
16#CD ->
16#BD;
16#CE ->
16#8B;
16#CF ->
16#8A;
16#D0 ->
16#70;
16#D1 ->
16#3E;
16#D2 ->
16#B5;
16#D3 ->
16#66;
16#D4 ->
16#48;
16#D5 ->
16#03;
16#D6 ->
16#F6;
16#D7 ->
16#0E;
16#D8 ->
16#61;
16#D9 ->
16#35;
16#DA ->
16#57;
16#DB ->
16#B9;
16#DC ->
16#86;
16#DD ->
16#C1;
16#DE ->
16#1D;
16#DF ->
16#9E;
16#E0 ->
16#E1;
16#E1 ->
16#F8;
16#E2 ->
16#98;
16#E3 ->
16#11;
16#E4 ->
16#69;
16#E5 ->
16#D9;
16#E6 ->
16#8E;
16#E7 ->
16#94;
16#E8 ->
16#9B;
16#E9 ->
16#1E;
16#EA ->
16#87;
16#EB ->
16#E9;
16#EC ->
16#CE;
16#ED ->
16#55;
16#EE ->
16#28;
16#EF ->
16#DF;
16#F0 ->
16#8C;
16#F1 ->
16#A1;
16#F2 ->
16#89;
16#F3 ->
16#0D;
16#F4 ->
16#BF;
16#F5 ->
16#E6;
16#F6 ->
16#42;
16#F7 ->
16#68;
16#F8 ->
16#41;
16#F9 ->
16#99;
16#FA ->
16#2D;
16#FB ->
16#0F;
16#FC ->
16#B0;
16#FD ->
16#54;
16#FE ->
16#BB;
_ ->
16#16
end.
-file("src/packkit/internal/aes.gleam", 91).
?DOC(false).
-spec sub_word(integer()) -> integer().
sub_word(Word) ->
B0 = sbox(erlang:'band'(erlang:'bsr'(Word, 24), 16#FF)),
B1 = sbox(erlang:'band'(erlang:'bsr'(Word, 16), 16#FF)),
B2 = sbox(erlang:'band'(erlang:'bsr'(Word, 8), 16#FF)),
B3 = sbox(erlang:'band'(Word, 16#FF)),
erlang:'bor'(
erlang:'bor'(
erlang:'bor'(erlang:'bsl'(B0, 24), erlang:'bsl'(B1, 16)),
erlang:'bsl'(B2, 8)
),
B3
).
-file("src/packkit/internal/aes.gleam", 186).
?DOC(false).
-spec sub_bytes(list(integer())) -> list(integer()).
sub_bytes(State) ->
gleam@list:map(State, fun sub_word/1).
-file("src/packkit/internal/aes.gleam", 146).
?DOC(false).
-spec encrypt_rounds(list(integer()), list(integer()), integer(), integer()) -> list(integer()).
encrypt_rounds(State, Round_keys, Round, Total) ->
case Round of
N when N =:= Total ->
After_sub = sub_bytes(State),
After_shift = shift_rows(After_sub),
add_round_key(After_shift, Round_keys, Total);
_ ->
After_sub@1 = sub_bytes(State),
After_shift@1 = shift_rows(After_sub@1),
After_mix = mix_columns(After_shift@1),
After_key = add_round_key(After_mix, Round_keys, Round),
encrypt_rounds(After_key, Round_keys, Round + 1, Total)
end.
-file("src/packkit/internal/aes.gleam", 133).
?DOC(false).
-spec encrypt_block(expanded_key(), bitstring()) -> {ok, bitstring()} |
{error, nil}.
encrypt_block(Key, Block) ->
case erlang:byte_size(Block) of
16 ->
State = bit_array_to_u32_words(Block, []),
State_xored = add_round_key(State, erlang:element(2, Key), 0),
Final_state = encrypt_rounds(
State_xored,
erlang:element(2, Key),
1,
erlang:element(3, Key)
),
{ok, u32_words_to_bit_array(Final_state, <<>>)};
_ ->
{error, nil}
end.
-file("src/packkit/internal/aes.gleam", 720).
?DOC(false).
-spec inv_sbox(integer()) -> integer().
inv_sbox(Byte) ->
case Byte of
16#00 ->
16#52;
16#01 ->
16#09;
16#02 ->
16#6A;
16#03 ->
16#D5;
16#04 ->
16#30;
16#05 ->
16#36;
16#06 ->
16#A5;
16#07 ->
16#38;
16#08 ->
16#BF;
16#09 ->
16#40;
16#0A ->
16#A3;
16#0B ->
16#9E;
16#0C ->
16#81;
16#0D ->
16#F3;
16#0E ->
16#D7;
16#0F ->
16#FB;
16#10 ->
16#7C;
16#11 ->
16#E3;
16#12 ->
16#39;
16#13 ->
16#82;
16#14 ->
16#9B;
16#15 ->
16#2F;
16#16 ->
16#FF;
16#17 ->
16#87;
16#18 ->
16#34;
16#19 ->
16#8E;
16#1A ->
16#43;
16#1B ->
16#44;
16#1C ->
16#C4;
16#1D ->
16#DE;
16#1E ->
16#E9;
16#1F ->
16#CB;
16#20 ->
16#54;
16#21 ->
16#7B;
16#22 ->
16#94;
16#23 ->
16#32;
16#24 ->
16#A6;
16#25 ->
16#C2;
16#26 ->
16#23;
16#27 ->
16#3D;
16#28 ->
16#EE;
16#29 ->
16#4C;
16#2A ->
16#95;
16#2B ->
16#0B;
16#2C ->
16#42;
16#2D ->
16#FA;
16#2E ->
16#C3;
16#2F ->
16#4E;
16#30 ->
16#08;
16#31 ->
16#2E;
16#32 ->
16#A1;
16#33 ->
16#66;
16#34 ->
16#28;
16#35 ->
16#D9;
16#36 ->
16#24;
16#37 ->
16#B2;
16#38 ->
16#76;
16#39 ->
16#5B;
16#3A ->
16#A2;
16#3B ->
16#49;
16#3C ->
16#6D;
16#3D ->
16#8B;
16#3E ->
16#D1;
16#3F ->
16#25;
16#40 ->
16#72;
16#41 ->
16#F8;
16#42 ->
16#F6;
16#43 ->
16#64;
16#44 ->
16#86;
16#45 ->
16#68;
16#46 ->
16#98;
16#47 ->
16#16;
16#48 ->
16#D4;
16#49 ->
16#A4;
16#4A ->
16#5C;
16#4B ->
16#CC;
16#4C ->
16#5D;
16#4D ->
16#65;
16#4E ->
16#B6;
16#4F ->
16#92;
16#50 ->
16#6C;
16#51 ->
16#70;
16#52 ->
16#48;
16#53 ->
16#50;
16#54 ->
16#FD;
16#55 ->
16#ED;
16#56 ->
16#B9;
16#57 ->
16#DA;
16#58 ->
16#5E;
16#59 ->
16#15;
16#5A ->
16#46;
16#5B ->
16#57;
16#5C ->
16#A7;
16#5D ->
16#8D;
16#5E ->
16#9D;
16#5F ->
16#84;
16#60 ->
16#90;
16#61 ->
16#D8;
16#62 ->
16#AB;
16#63 ->
16#00;
16#64 ->
16#8C;
16#65 ->
16#BC;
16#66 ->
16#D3;
16#67 ->
16#0A;
16#68 ->
16#F7;
16#69 ->
16#E4;
16#6A ->
16#58;
16#6B ->
16#05;
16#6C ->
16#B8;
16#6D ->
16#B3;
16#6E ->
16#45;
16#6F ->
16#06;
16#70 ->
16#D0;
16#71 ->
16#2C;
16#72 ->
16#1E;
16#73 ->
16#8F;
16#74 ->
16#CA;
16#75 ->
16#3F;
16#76 ->
16#0F;
16#77 ->
16#02;
16#78 ->
16#C1;
16#79 ->
16#AF;
16#7A ->
16#BD;
16#7B ->
16#03;
16#7C ->
16#01;
16#7D ->
16#13;
16#7E ->
16#8A;
16#7F ->
16#6B;
16#80 ->
16#3A;
16#81 ->
16#91;
16#82 ->
16#11;
16#83 ->
16#41;
16#84 ->
16#4F;
16#85 ->
16#67;
16#86 ->
16#DC;
16#87 ->
16#EA;
16#88 ->
16#97;
16#89 ->
16#F2;
16#8A ->
16#CF;
16#8B ->
16#CE;
16#8C ->
16#F0;
16#8D ->
16#B4;
16#8E ->
16#E6;
16#8F ->
16#73;
16#90 ->
16#96;
16#91 ->
16#AC;
16#92 ->
16#74;
16#93 ->
16#22;
16#94 ->
16#E7;
16#95 ->
16#AD;
16#96 ->
16#35;
16#97 ->
16#85;
16#98 ->
16#E2;
16#99 ->
16#F9;
16#9A ->
16#37;
16#9B ->
16#E8;
16#9C ->
16#1C;
16#9D ->
16#75;
16#9E ->
16#DF;
16#9F ->
16#6E;
16#A0 ->
16#47;
16#A1 ->
16#F1;
16#A2 ->
16#1A;
16#A3 ->
16#71;
16#A4 ->
16#1D;
16#A5 ->
16#29;
16#A6 ->
16#C5;
16#A7 ->
16#89;
16#A8 ->
16#6F;
16#A9 ->
16#B7;
16#AA ->
16#62;
16#AB ->
16#0E;
16#AC ->
16#AA;
16#AD ->
16#18;
16#AE ->
16#BE;
16#AF ->
16#1B;
16#B0 ->
16#FC;
16#B1 ->
16#56;
16#B2 ->
16#3E;
16#B3 ->
16#4B;
16#B4 ->
16#C6;
16#B5 ->
16#D2;
16#B6 ->
16#79;
16#B7 ->
16#20;
16#B8 ->
16#9A;
16#B9 ->
16#DB;
16#BA ->
16#C0;
16#BB ->
16#FE;
16#BC ->
16#78;
16#BD ->
16#CD;
16#BE ->
16#5A;
16#BF ->
16#F4;
16#C0 ->
16#1F;
16#C1 ->
16#DD;
16#C2 ->
16#A8;
16#C3 ->
16#33;
16#C4 ->
16#88;
16#C5 ->
16#07;
16#C6 ->
16#C7;
16#C7 ->
16#31;
16#C8 ->
16#B1;
16#C9 ->
16#12;
16#CA ->
16#10;
16#CB ->
16#59;
16#CC ->
16#27;
16#CD ->
16#80;
16#CE ->
16#EC;
16#CF ->
16#5F;
16#D0 ->
16#60;
16#D1 ->
16#51;
16#D2 ->
16#7F;
16#D3 ->
16#A9;
16#D4 ->
16#19;
16#D5 ->
16#B5;
16#D6 ->
16#4A;
16#D7 ->
16#0D;
16#D8 ->
16#2D;
16#D9 ->
16#E5;
16#DA ->
16#7A;
16#DB ->
16#9F;
16#DC ->
16#93;
16#DD ->
16#C9;
16#DE ->
16#9C;
16#DF ->
16#EF;
16#E0 ->
16#A0;
16#E1 ->
16#E0;
16#E2 ->
16#3B;
16#E3 ->
16#4D;
16#E4 ->
16#AE;
16#E5 ->
16#2A;
16#E6 ->
16#F5;
16#E7 ->
16#B0;
16#E8 ->
16#C8;
16#E9 ->
16#EB;
16#EA ->
16#BB;
16#EB ->
16#3C;
16#EC ->
16#83;
16#ED ->
16#53;
16#EE ->
16#99;
16#EF ->
16#61;
16#F0 ->
16#17;
16#F1 ->
16#2B;
16#F2 ->
16#04;
16#F3 ->
16#7E;
16#F4 ->
16#BA;
16#F5 ->
16#77;
16#F6 ->
16#D6;
16#F7 ->
16#26;
16#F8 ->
16#E1;
16#F9 ->
16#69;
16#FA ->
16#14;
16#FB ->
16#63;
16#FC ->
16#55;
16#FD ->
16#21;
16#FE ->
16#0C;
_ ->
16#7D
end.
-file("src/packkit/internal/aes.gleam", 303).
?DOC(false).
-spec inv_sub_word(integer()) -> integer().
inv_sub_word(Word) ->
B0 = inv_sbox(erlang:'band'(erlang:'bsr'(Word, 24), 16#FF)),
B1 = inv_sbox(erlang:'band'(erlang:'bsr'(Word, 16), 16#FF)),
B2 = inv_sbox(erlang:'band'(erlang:'bsr'(Word, 8), 16#FF)),
B3 = inv_sbox(erlang:'band'(Word, 16#FF)),
erlang:'bor'(
erlang:'bor'(
erlang:'bor'(erlang:'bsl'(B0, 24), erlang:'bsl'(B1, 16)),
erlang:'bsl'(B2, 8)
),
B3
).
-file("src/packkit/internal/aes.gleam", 299).
?DOC(false).
-spec inv_sub_bytes(list(integer())) -> list(integer()).
inv_sub_bytes(State) ->
gleam@list:map(State, fun inv_sub_word/1).
-file("src/packkit/internal/aes.gleam", 276).
?DOC(false).
-spec decrypt_rounds(list(integer()), list(integer()), integer()) -> list(integer()).
decrypt_rounds(State, Round_keys, Round) ->
case Round of
0 ->
After_shift = inv_shift_rows(State),
After_sub = inv_sub_bytes(After_shift),
add_round_key(After_sub, Round_keys, 0);
_ ->
After_shift@1 = inv_shift_rows(State),
After_sub@1 = inv_sub_bytes(After_shift@1),
After_key = add_round_key(After_sub@1, Round_keys, Round),
After_mix = inv_mix_columns(After_key),
decrypt_rounds(After_mix, Round_keys, Round - 1)
end.
-file("src/packkit/internal/aes.gleam", 263).
?DOC(false).
-spec decrypt_block(expanded_key(), bitstring()) -> {ok, bitstring()} |
{error, nil}.
decrypt_block(Key, Block) ->
case erlang:byte_size(Block) of
16 ->
State = bit_array_to_u32_words(Block, []),
State_xored = add_round_key(
State,
erlang:element(2, Key),
erlang:element(3, Key)
),
Final_state = decrypt_rounds(
State_xored,
erlang:element(2, Key),
erlang:element(3, Key) - 1
),
{ok, u32_words_to_bit_array(Final_state, <<>>)};
_ ->
{error, nil}
end.
-file("src/packkit/internal/aes.gleam", 85).
?DOC(false).
-spec rotate_word(integer()) -> integer().
rotate_word(Word) ->
High = erlang:'band'(erlang:'bsl'(Word, 8), 16#FFFFFFFF),
Low = erlang:'bsr'(Word, 24),
erlang:'bor'(High, Low).
-file("src/packkit/internal/aes.gleam", 53).
?DOC(false).
-spec expand_loop(list(integer()), integer(), integer(), integer()) -> list(integer()).
expand_loop(Reversed, Index, Nk, Total) ->
gleam@bool:guard(
Index >= Total,
Reversed,
fun() ->
case {Reversed, gleam@list:first(gleam@list:drop(Reversed, Nk - 1))} of
{[Previous | _], {ok, Word_nk_ago}} ->
Transformed = case case Nk of
0 -> 0;
Gleam@denominator -> Index rem Gleam@denominator
end of
0 ->
Rotated = rotate_word(Previous),
Subbed = sub_word(Rotated),
Rcon = rcon_value(case Nk of
0 -> 0;
Gleam@denominator@1 -> Index div Gleam@denominator@1
end),
erlang:'bxor'(Subbed, Rcon);
4 when Nk > 6 ->
sub_word(Previous);
_ ->
Previous
end,
Next = erlang:'bxor'(Word_nk_ago, Transformed),
expand_loop([Next | Reversed], Index + 1, Nk, Total);
{_, _} ->
Reversed
end
end
).
-file("src/packkit/internal/aes.gleam", 45).
?DOC(false).
-spec do_expand(list(integer()), integer(), integer()) -> expanded_key().
do_expand(Key_words, Nk, Rounds) ->
Total_words = 4 * (Rounds + 1),
Reversed_initial = lists:reverse(Key_words),
Reversed_all = expand_loop(Reversed_initial, Nk, Nk, Total_words),
Round_keys = lists:reverse(Reversed_all),
{expanded_key, Round_keys, Rounds}.
-file("src/packkit/internal/aes.gleam", 34).
?DOC(false).
-spec expand_key(bitstring()) -> {ok, expanded_key()} | {error, nil}.
expand_key(Key) ->
Key_words = bit_array_to_u32_words(Key, []),
Nk = erlang:length(Key_words),
case Nk of
4 ->
{ok, do_expand(Key_words, 4, 10)};
6 ->
{ok, do_expand(Key_words, 6, 12)};
8 ->
{ok, do_expand(Key_words, 8, 14)};
_ ->
{error, nil}
end.