BLu85 / AES-GCM-128-192-256-bits

Configurable AES-GCM IP (128, 192, 256 bits)
19 stars 5 forks source link

AES-GCM NIST Test Vectors - Not Getting Expected Results #5

Closed dmyers38 closed 8 months ago

dmyers38 commented 8 months ago

Hi @BLu85,

I have a few questions about this AES-GCM core and was wondering if you could answer them. I am particularly interested in the 256-bit version. I have generated the files from the configuration scripts and implemented them into two different testbenches. When comparing to another AES-GCM core I get different results. I followed the timing diagram shown in the README, but it is possible that I may still have an implementation issue. Also, has this core been tested using NIST test vectors? I cannot get the expected results when using this core.

The NIST test vector that I am currently using is the following:

[Keylen = 256]
[IVlen = 96]
[PTlen = 128]
[AADlen = 128]
[Taglen = 128]

Count = 0
Key = 92e11dcdaa866f5ce790fd24501f92509aacf4cb8b1339d50c9c1240935dd08b
IV = ac93a1a6145299bde902f21a
PT = 2d71bcfa914e4ac045b2aa60955fad24
AAD = 1e0889016f67601c8ebea4943bc23ad6
CT = 8995ae2e6df3dbf96fac7b7137bae67f
Tag = eca5aa77d51d4a0a14d9c51e1da474ab

However, instead I get the following CT and Tag:

CT = 56eb7bf1f2aebfdcb1ae519f5a38d61f
Tag = 3252d0baf357703e0f017e647a54aea9

Here are the simulation waveforms in case anything pops out as incorrect:

image

Is there a misunderstanding on my end based on the attached waveforms?

Thank you for your time and consideration!

BLu85 commented 8 months ago

Hi @dmyers38

I tried the core with few (not all) the NIST vectors. The project has a testbench included that you might want to try. The DUT runs against a model created using pyCryptodome. Could it be just a matter of loading the data in the wrong byte order (LSB vs MSB)? I will givie it a go when I get some time.

dmyers38 commented 8 months ago

@BLu85, I have tried a variety of simulations at this point. I seemingly got it working with your testbench (see attached waveform file). I had to hardcode the PT and AAD, but it does give the correct NIST output CT and Tag. However, I still cannot get it to work with any of my simulations (could still be an implementation issue). No matter what I do I end up with aforementioned CT and Tag. I don't believe it could be a byte order issue since the waveforms all show the same inputs. I've matched my simulation to follow the same timing as your testbench.

Waveform File - aes_dump.zip

I can send a VCD of one of my simulations too if that would be better than the image above.

Thank you again for your time.

BLu85 commented 8 months ago

As you said the input signals seem to be the same. It would be worth dumping your simulation in a VCD (or better .ghw file) so I can explore the sub-blocks and understand what is the source of the problem. Also, what python command did you run to get the IP configuration for your case and for the python TB?

BLu85 commented 8 months ago

Looking at the waveforms in the image you posted, I noticed that the number of clocks between the assertion of the signal aes_gcm_icb_start_cnt_i and the assertion of the signal aes_gcm_ready_o, is less than 14 clocks. That number of clocks is the minimum needed to generate the H and J0 vectors for the AES 256 bits. Probably a misconfiguration of the IP has set it to a 128 bits key. Could you compare the generated .vhd files in the TB folder (when you said you got the correct results) with the ones that gave you the wrong result?

dmyers38 commented 8 months ago

Attached is a VCD of the simulation from the waveforms above (the simulator I am using does not export to GHW). It should be noted that the testbench is driving on the negative edge of the clock to avoid race condition issues on the positive edge. However, my other simulations drive the core via FIFOs and an FSM on the positive edge of the clock. They all result in the same incorrect CT and Tag.

Also, what python command did you run to get the IP configuration for your case and for the python TB?

I used python3 gcm_config.py -m 256 -b enc -p 0 -s L to generate the IP and python3 gcm_testbench.py -m 256 -b enc -s L -k 92e11dcdaa866f5ce790fd24501f92509aacf4cb8b1339d50c9c1240935dd08b -i ac93a1a6145299bde902f21a -g for the testbench.

Could you compare the generated .vhd files in the TB folder (when you said you got the correct results) with the ones that gave you the wrong result?

The generated files in the TB and SRC directories show no differences.

Waveforms - sim_aes_dump.zip

dmyers38 commented 8 months ago

Well, I found my issue. I have been instantiating the aes_gcm module instead of the top_aes_gcm module so the parameters were not being overwritten. The top-level was used as the reference for the port mapping but I must have forgot to update the module name. Of course, this carried over when copying/pasting the instantiation to the other testbenches. Regardless, thank you for your time and consideration.

BLu85 commented 8 months ago

This commit adds the possibility to externally load the key, iv, aad and data. NIST test vectors can be tested as: python3 gcm_testbench.py -m 256 -b enc -s L -k 92e11dcdaa866f5ce790fd24501f92509aacf4cb8b1339d50c9c1240935dd08b -i ac93a1a6145299bde902f21a -a 1e0889016f67601c8ebea4943bc23ad6 -d 2d71bcfa914e4ac045b2aa60955fad24