• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

famoser / elliptic / 16437972044

22 Jul 2025 07:42AM UTC coverage: 95.58% (+0.1%) from 95.437%
16437972044

Pull #12

github

web-flow
Merge 90594b1b9 into 85d13e57a
Pull Request #12: WIP: Add montgomery

567 of 589 new or added lines in 35 files covered. (96.26%)

1211 of 1267 relevant lines covered (95.58%)

22.1 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

96.97
/src/Serializer/SECSerializer.php
1
<?php
2

3
namespace Famoser\Elliptic\Serializer;
4

5
use Famoser\Elliptic\Primitives\Curve;
6
use Famoser\Elliptic\Primitives\Point;
7
use Famoser\Elliptic\Serializer\PointDecoder\PointDecoderException;
8
use Famoser\Elliptic\Serializer\SEC\SECEncoding;
9
use Famoser\Elliptic\Serializer\SEC\SECPointDecoderInterface;
10

11
/**
12
 * implements serialization as described in https://www.secg.org/SEC1-Ver-1.0.pdf
13
 */
14
class SECSerializer
15
{
16
    private readonly int $pointOctetLength;
17

18
    public function __construct(private readonly Curve $curve, private readonly SECPointDecoderInterface $pointDecoder, private readonly SECEncoding $preferredEncoding = SECEncoding::COMPRESSED)
3✔
19
    {
20
        $this->pointOctetLength = (int) ceil((float) strlen(gmp_strval($this->curve->getP(), 2)) / 8);
3✔
21
    }
22

23
    /**
24
     * implements https://wdecoderww.secg.org/SEC1-Ver-1.0.pdf 2.3.4
25
     *
26
     * @throws PointDecoderException|SerializerException
27
     */
28
    public function deserialize(string $hex): Point
3✔
29
    {
30
        if ($hex === '00') {
3✔
31
            return Point::createInfinity();
1✔
32
        }
33

34
        $compressedFormatOctetLength = 1 + $this->pointOctetLength;
2✔
35
        if (strlen($hex) === 2 * $compressedFormatOctetLength && (str_starts_with($hex, '02') || str_starts_with($hex, '03'))) {
2✔
36
            $x = gmp_init(substr($hex, 2), 16);
1✔
37
            $isEvenY = str_starts_with($hex, '02');
1✔
38

39
            return $this->pointDecoder->fromXCoordinate($x, $isEvenY);
1✔
40
        }
41

42
        $uncompressedFormatOctetLength = 1 + 2 * $this->pointOctetLength;
1✔
43
        if (strlen($hex) === 2 * $uncompressedFormatOctetLength && str_starts_with($hex, '04')) {
1✔
44
            $pointHexLength = 2 * $this->pointOctetLength;
1✔
45
            $x = gmp_init(substr($hex, 2, $pointHexLength), 16);
1✔
46
            $y = gmp_init(substr($hex, 2 + $pointHexLength), 16);
1✔
47

48
            return $this->pointDecoder->fromCoordinates($x, $y);
1✔
49
        }
50

NEW
51
        throw new SerializerException('Unknown deserialization format.');
×
52
    }
53

54
    /**
55
     * implements https://www.secg.org/SEC1-Ver-1.0.pdf 2.3.3
56
     */
57
    public function serialize(Point $point): string
3✔
58
    {
59
        if ($point->isInfinity()) {
3✔
60
            return '00';
1✔
61
        }
62

63
        return match ($this->preferredEncoding) {
2✔
64
            SECEncoding::COMPRESSED => $this->serializeCompressed($point),
2✔
65
            SECEncoding::UNCOMPRESSED => $this->serializeUncompressed($point)
2✔
66
        };
2✔
67
    }
68

69
    private function serializeCompressed(Point $point): string
1✔
70
    {
71
        $x = str_pad(gmp_strval($point->x, 16), $this->pointOctetLength * 2, '0', STR_PAD_LEFT);
1✔
72

73
        $isEven = gmp_cmp(gmp_mod($point->y, 2), 0) === 0;
1✔
74
        $prefix = $isEven ? '02' : '03';
1✔
75

76
        return $prefix . $x;
1✔
77
    }
78

79
    private function serializeUncompressed(Point $point): string
1✔
80
    {
81
        $x = str_pad(gmp_strval($point->x, 16), $this->pointOctetLength * 2, '0', STR_PAD_LEFT);
1✔
82
        $y = str_pad(gmp_strval($point->y, 16), $this->pointOctetLength * 2, '0', STR_PAD_LEFT);
1✔
83

84
        return '04' . $x . $y;
1✔
85
    }
86
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc