Coverage for /pythoncovmergedfiles/medio/medio/usr/local/lib/python3.11/site-packages/Crypto/Util/Padding.py: 24%
Shortcuts on this page
r m x toggle line displays
j k next/prev highlighted chunk
0 (zero) top of page
1 (one) first highlighted chunk
Shortcuts on this page
r m x toggle line displays
j k next/prev highlighted chunk
0 (zero) top of page
1 (one) first highlighted chunk
1#
2# Util/Padding.py : Functions to manage padding
3#
4# SPDX-FileCopyrightText: 2014 Legrandin <helderijs@gmail.com>
5# SPDX-License-Identifier: BSD-2-Clause
7from __future__ import annotations
9from typing import Optional
11__all__ = ["pad", "unpad"]
14def pad(data_to_pad: bytes, block_size: int, style: Optional[str] = "pkcs7") -> bytes:
15 """Apply standard padding.
17 Args:
18 data_to_pad (byte string):
19 The data that needs to be padded.
20 block_size (integer):
21 The block boundary to use for padding. The output length is guaranteed
22 to be a multiple of :data:`block_size`.
23 style (string):
24 Padding algorithm. It can be *'pkcs7'* (default), *'iso7816'* or *'x923'*.
26 Return:
27 byte string : the original data with the appropriate padding added at the end.
28 """
30 padding_len = block_size - len(data_to_pad) % block_size
32 if style == "pkcs7":
33 padding = bytes([padding_len]) * padding_len
34 elif style == "x923":
35 padding = bytes([0]) * (padding_len - 1) + bytes([padding_len])
36 elif style == "iso7816":
37 padding = bytes([128]) + bytes([0]) * (padding_len - 1)
38 else:
39 raise ValueError("Unknown padding style")
41 return data_to_pad + padding
44def unpad(padded_data: bytes, block_size: int, style: Optional[str] = "pkcs7") -> bytes:
45 """Remove standard padding.
47 Args:
48 padded_data (byte string):
49 A piece of data with padding that needs to be stripped.
50 block_size (integer):
51 The block boundary to use for padding. The input length
52 must be a multiple of :data:`block_size`.
53 style (string):
54 Padding algorithm. It can be *'pkcs7'* (default), *'iso7816'* or *'x923'*.
55 Return:
56 byte string : data without padding.
57 Raises:
58 ValueError: if the padding is incorrect.
59 """
61 pdata_len = len(padded_data)
63 if pdata_len == 0:
64 raise ValueError("Zero-length input cannot be unpadded")
66 if pdata_len % block_size:
67 raise ValueError("Input data is not padded")
69 if style in ("pkcs7", "x923"):
70 padding_len = padded_data[-1]
72 if padding_len < 1 or padding_len > min(block_size, pdata_len):
73 raise ValueError("Padding is incorrect.")
75 if style == "pkcs7":
76 if padded_data[-padding_len:] != bytes([padding_len]) * padding_len:
77 raise ValueError("PKCS#7 padding is incorrect.")
78 else:
79 if padded_data[-padding_len:-1] != bytes([0]) * (padding_len - 1):
80 raise ValueError("ANSI X.923 padding is incorrect.")
82 elif style == "iso7816":
83 padding_len = pdata_len - padded_data.rfind(bytes([128]))
85 if padding_len < 1 or padding_len > min(block_size, pdata_len):
86 raise ValueError("Padding is incorrect.")
88 if padding_len > 1 and padded_data[1 - padding_len :] != bytes([0]) * (padding_len - 1):
89 raise ValueError("ISO 7816-4 padding is incorrect.")
90 else:
91 raise ValueError("Unknown padding style")
93 return padded_data[:-padding_len]