xref: /freebsd/crypto/openssl/util/perl/TLSProxy/CertificateRequest.pm (revision e7be843b4a162e68651d3911f0357ed464915629)
1*e7be843bSPierre Pronchery# Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved.
2e0c4386eSCy Schubert#
3e0c4386eSCy Schubert# Licensed under the Apache License 2.0 (the "License").  You may not use
4e0c4386eSCy Schubert# this file except in compliance with the License.  You can obtain a copy
5e0c4386eSCy Schubert# in the file LICENSE in the source distribution or at
6e0c4386eSCy Schubert# https://www.openssl.org/source/license.html
7e0c4386eSCy Schubert
8e0c4386eSCy Schubertuse strict;
9e0c4386eSCy Schubert
10e0c4386eSCy Schubertpackage TLSProxy::CertificateRequest;
11e0c4386eSCy Schubert
12e0c4386eSCy Schubertuse vars '@ISA';
13e0c4386eSCy Schubertpush @ISA, 'TLSProxy::Message';
14e0c4386eSCy Schubert
15e0c4386eSCy Schubertsub new
16e0c4386eSCy Schubert{
17e0c4386eSCy Schubert    my $class = shift;
18*e7be843bSPierre Pronchery    my ($isdtls,
19*e7be843bSPierre Pronchery        $server,
20*e7be843bSPierre Pronchery        $msgseq,
21*e7be843bSPierre Pronchery        $msgfrag,
22*e7be843bSPierre Pronchery        $msgfragoffs,
23e0c4386eSCy Schubert        $data,
24e0c4386eSCy Schubert        $records,
25e0c4386eSCy Schubert        $startoffset,
26e0c4386eSCy Schubert        $message_frag_lens) = @_;
27e0c4386eSCy Schubert
28e0c4386eSCy Schubert    my $self = $class->SUPER::new(
29*e7be843bSPierre Pronchery        $isdtls,
30e0c4386eSCy Schubert        $server,
31e0c4386eSCy Schubert        TLSProxy::Message::MT_CERTIFICATE_REQUEST,
32*e7be843bSPierre Pronchery        $msgseq,
33*e7be843bSPierre Pronchery        $msgfrag,
34*e7be843bSPierre Pronchery        $msgfragoffs,
35e0c4386eSCy Schubert        $data,
36e0c4386eSCy Schubert        $records,
37e0c4386eSCy Schubert        $startoffset,
38e0c4386eSCy Schubert        $message_frag_lens);
39e0c4386eSCy Schubert
40e0c4386eSCy Schubert    $self->{extension_data} = "";
41e0c4386eSCy Schubert
42e0c4386eSCy Schubert    return $self;
43e0c4386eSCy Schubert}
44e0c4386eSCy Schubert
45e0c4386eSCy Schubertsub parse
46e0c4386eSCy Schubert{
47e0c4386eSCy Schubert    my $self = shift;
48e0c4386eSCy Schubert    my $ptr = 1;
49e0c4386eSCy Schubert
50e0c4386eSCy Schubert    if (TLSProxy::Proxy->is_tls13()) {
51e0c4386eSCy Schubert        my $request_ctx_len = unpack('C', $self->data);
52e0c4386eSCy Schubert        my $request_ctx = substr($self->data, $ptr, $request_ctx_len);
53e0c4386eSCy Schubert        $ptr += $request_ctx_len;
54e0c4386eSCy Schubert
55e0c4386eSCy Schubert        my $extensions_len = unpack('n', substr($self->data, $ptr));
56e0c4386eSCy Schubert        $ptr += 2;
57e0c4386eSCy Schubert        my $extension_data = substr($self->data, $ptr);
58e0c4386eSCy Schubert        if (length($extension_data) != $extensions_len) {
59e0c4386eSCy Schubert            die "Invalid extension length\n";
60e0c4386eSCy Schubert        }
61e0c4386eSCy Schubert        my %extensions = ();
62e0c4386eSCy Schubert        while (length($extension_data) >= 4) {
63e0c4386eSCy Schubert            my ($type, $size) = unpack("nn", $extension_data);
64e0c4386eSCy Schubert            my $extdata = substr($extension_data, 4, $size);
65e0c4386eSCy Schubert            $extension_data = substr($extension_data, 4 + $size);
66e0c4386eSCy Schubert            $extensions{$type} = $extdata;
67e0c4386eSCy Schubert        }
68e0c4386eSCy Schubert        $self->extension_data(\%extensions);
69e0c4386eSCy Schubert
70e0c4386eSCy Schubert        print "    Extensions Len:".$extensions_len."\n";
71e0c4386eSCy Schubert    }
72e0c4386eSCy Schubert    # else parse TLSv1.2 version - we don't support that at the moment
73e0c4386eSCy Schubert}
74e0c4386eSCy Schubert
75e0c4386eSCy Schubert#Reconstruct the on-the-wire message data following changes
76e0c4386eSCy Schubertsub set_message_contents
77e0c4386eSCy Schubert{
78e0c4386eSCy Schubert    my $self = shift;
79e0c4386eSCy Schubert    my $data;
80e0c4386eSCy Schubert    my $extensions = "";
81e0c4386eSCy Schubert
82e0c4386eSCy Schubert    foreach my $key (keys %{$self->extension_data}) {
83e0c4386eSCy Schubert        my $extdata = ${$self->extension_data}{$key};
84e0c4386eSCy Schubert        $extensions .= pack("n", $key);
85e0c4386eSCy Schubert        $extensions .= pack("n", length($extdata));
86e0c4386eSCy Schubert        $extensions .= $extdata;
87e0c4386eSCy Schubert    }
88e0c4386eSCy Schubert
89e0c4386eSCy Schubert    $data = pack('n', length($extensions));
90e0c4386eSCy Schubert    $data .= $extensions;
91e0c4386eSCy Schubert    $self->data($data);
92e0c4386eSCy Schubert}
93e0c4386eSCy Schubert
94e0c4386eSCy Schubert#Read/write accessors
95e0c4386eSCy Schubertsub extension_data
96e0c4386eSCy Schubert{
97e0c4386eSCy Schubert    my $self = shift;
98e0c4386eSCy Schubert    if (@_) {
99e0c4386eSCy Schubert        $self->{extension_data} = shift;
100e0c4386eSCy Schubert    }
101e0c4386eSCy Schubert    return $self->{extension_data};
102e0c4386eSCy Schubert}
103e0c4386eSCy Schubertsub set_extension
104e0c4386eSCy Schubert{
105e0c4386eSCy Schubert    my ($self, $ext_type, $ext_data) = @_;
106e0c4386eSCy Schubert    $self->{extension_data}{$ext_type} = $ext_data;
107e0c4386eSCy Schubert}
108e0c4386eSCy Schubertsub delete_extension
109e0c4386eSCy Schubert{
110e0c4386eSCy Schubert    my ($self, $ext_type) = @_;
111e0c4386eSCy Schubert    delete $self->{extension_data}{$ext_type};
112e0c4386eSCy Schubert}
113e0c4386eSCy Schubert1;
114