[#insns-aes64ks1i, reftext="AES Key Schedule Instruction 1 (RV64)"]
=== aes64ks1i

Synopsis::
This instruction implements part of the KeySchedule operation for the
AES Block cipher involving the SBox operation.

Mnemonic::
aes64ks1i rd, rs1, rnum

Encoding::
[wavedrom, , svg]
....
{reg:[
{bits: 7, name: 0x13},
{bits: 5, name: 'rd'},
{bits: 3, name: 0x1},
{bits: 5, name: 'rs1'},
{bits: 4, name: 'rnum'},
{bits: 1, name: 0x1},
{bits: 5, name: 0x18},
{bits: 2, name: 0},
]}
....

Description:: 
This instruction implements the rotation, SubBytes and Round Constant
addition steps of the AES block cipher Key Schedule.
This instruction must _always_ be implemented such that its execution
latency does not depend on the data being operated on.
Note that `rnum` must be in the range `0x0..0xA`.
The values `0xB..0xF` are reserved.

Operation::
[source,sail]
--
function clause execute (AES64KS1I(rnum, rs1, rd)) = {
  if(unsigned(rnum) > 10) then {
    handle_illegal();  RETIRE_SUCCESS
  } else {
    let tmp1 : bits(32) = X(rs1)[63..32];
    let rc   : bits(32) = aes_decode_rcon(rnum); /* round number -> round constant */
    let tmp2 : bits(32) = if (rnum ==0xA) then tmp1 else ror32(tmp1, 8);
    let tmp3 : bits(32) = aes_subword_fwd(tmp2);
    let result : bits(64) = (tmp3 ^ rc) @ (tmp3 ^ rc);
    X(rd) = EXTZ(result);
    RETIRE_SUCCESS
  }
}
--

Included in::
[%header,cols="4,2,2"]
|===
|Extension
|Minimum version
|Lifecycle state

| <<zkne>> (RV64)
| v1.0.0
| Frozen
| <<zknd>> (RV64)
| v1.0.0
| Frozen
| <<zkn>> (RV64)
| v1.0.0
| Frozen
| <<zk>> (RV64)
| v1.0.0
| Frozen
|===


