aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorJán Jančár2023-10-02 19:19:03 +0200
committerGitHub2023-10-02 19:19:03 +0200
commit7316ceac35ced91d53d879a4c6ca4d1177d4abe2 (patch)
tree4ed4b28614510cfc9f02b5bea4c44485fb95fb05
parentd05ff78a0b51aad0e9062be992ab7f6f19765b09 (diff)
parent777c12ea60087d9155f6408a908b878fea94923c (diff)
downloadpyecsca-notebook-7316ceac35ced91d53d879a4c6ca4d1177d4abe2.tar.gz
pyecsca-notebook-7316ceac35ced91d53d879a4c6ca4d1177d4abe2.tar.zst
pyecsca-notebook-7316ceac35ced91d53d879a4c6ca4d1177d4abe2.zip
Merge pull request #2 from andrr3j/DPA
DPA notebook
-rw-r--r--DPA.ipynb264
1 files changed, 264 insertions, 0 deletions
diff --git a/DPA.ipynb b/DPA.ipynb
new file mode 100644
index 0000000..382cacc
--- /dev/null
+++ b/DPA.ipynb
@@ -0,0 +1,264 @@
+{
+ "cells": [
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "# Differential power analysis on pyecsca emulated traces"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "### Setup"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "from pyecsca.ec.mult import LTRMultiplier\n",
+ "from pyecsca.ec.mod import Mod\n",
+ "from pyecsca.ec.point import Point, InfinityPoint\n",
+ "from pyecsca.ec.model import ShortWeierstrassModel\n",
+ "from pyecsca.ec.curve import EllipticCurve\n",
+ "from pyecsca.ec.params import DomainParameters\n",
+ "from pyecsca.sca.attack.DPA import DPA\n",
+ "from pyecsca.sca.attack.leakage_model import HammingWeight\n",
+ "from pyecsca.sca.target.emulator import EmulatorTarget\n",
+ "from random import randint\n",
+ "import holoviews as hv"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "hv.extension(\"bokeh\")\n"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "model = ShortWeierstrassModel()\n",
+ "coords = model.coordinates[\"projective\"]\n",
+ "p = 0xd7d1247f\n",
+ "a = Mod(0xa4a44016, p)\n",
+ "b = Mod(0x73f76716, p)\n",
+ "n = 0xd7d2a475\n",
+ "h = 1\n",
+ "gx, gy, gz = Mod(0x54eed6d7, p), Mod(0x6f1e55ac, p), Mod(1, p)\n",
+ "generator = Point(coords, X=gx, Y=gy, Z=gz)\n",
+ "neutral = InfinityPoint(coords)\n",
+ "\n",
+ "curve = EllipticCurve(model, coords, p, neutral, {\"a\": a, \"b\": b})\n",
+ "params = DomainParameters(curve, generator, n, h)\n",
+ "\n",
+ "add = coords.formulas[\"add-2015-rcb\"]\n",
+ "dbl = coords.formulas[\"dbl-2015-rcb\"]\n",
+ "scl = coords.formulas[\"z\"]\n",
+ "\n",
+ "mult = LTRMultiplier(add, dbl, None)"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "scalar_bit_length = 8\n",
+ "secret_scalar = randint(128, 255)\n",
+ "print(secret_scalar)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "### Emulation of traces"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "num_of_traces = 5000"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "emulator = EmulatorTarget(model, coords, mult)\n",
+ "emulator.set_params(params)\n",
+ "emulator.set_leakage_model(HammingWeight())"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "points, traces = emulator.emulate_scalar_mult_traces(num_of_traces, secret_scalar)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "### DPA"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "mult.init(params, params.generator)\n",
+ "real_pub_key = mult.multiply(secret_scalar)\n",
+ "dpa = DPA(points, traces, mult, params)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "#### Recover the 8-bit scalar bit by bit"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "recovered_scalar = 128 #1000 0000"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "recovered_scalar = dpa.recover_bit(recovered_scalar, 1, scalar_bit_length, real_pub_key)\n",
+ "print(f\"Recovered scalar after recovering 2. bit of the secret scalar: {recovered_scalar} = {recovered_scalar:b}\")"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "# Difference of means when guessing 2. bit (guessed scalar 192 = 1100 0000)\n",
+ "dpa.plot_difference_of_means(dpa.doms['guess_one'][0])"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "# Difference of means when guessing 2. bit (guessed scalar 128 = 1000 0000)\n",
+ "dpa.plot_difference_of_means(dpa.doms['guess_zero'][0])"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 24,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "# We can do this for each bit of the scalar\n",
+ "for i in range(2, scalar_bit_length):\n",
+ " recovered_scalar = dpa.recover_bit(recovered_scalar, i, scalar_bit_length, real_pub_key)\n",
+ " print(f\"Recovered scalar after recovering {i + 1}. bit of the secret scalar: {recovered_scalar} = {recovered_scalar:b}\")\n",
+ "print(recovered_scalar == secret_scalar)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "#### Recover the whole 8-bit scalar"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "recovered_scalar = dpa.perform(scalar_bit_length, real_pub_key)\n",
+ "print(recovered_scalar)\n",
+ "print(recovered_scalar == secret_scalar)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {},
+ "source": [
+ "#### We can look at the difference of means after last recovered bit for both zero guess and one guess"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "# Zero guess\n",
+ "dpa.plot_difference_of_means(dpa.doms['guess_zero'][-1])"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "# One guess\n",
+ "dpa.plot_difference_of_means(dpa.doms['guess_one'][-1])"
+ ]
+ }
+ ],
+ "metadata": {
+ "kernelspec": {
+ "display_name": "venv",
+ "language": "python",
+ "name": "python3"
+ },
+ "language_info": {
+ "codemirror_mode": {
+ "name": "ipython",
+ "version": 3
+ },
+ "file_extension": ".py",
+ "mimetype": "text/x-python",
+ "name": "python",
+ "nbconvert_exporter": "python",
+ "pygments_lexer": "ipython3",
+ "version": "3.9.16"
+ },
+ "orig_nbformat": 4
+ },
+ "nbformat": 4,
+ "nbformat_minor": 2
+}