PluginProbe
Defender Security – Malware Scanner, Login Security & Firewall / 6.0.1
Defender Security – Malware Scanner, Login Security & Firewall v6.0.1
6.3.0 6.2.3 6.2.4 6.2.0 6.2.1 6.2.2 6.1.0 5.3.1 5.4.0 5.4.1 5.5.0 5.5.1 5.6.0 5.6.1 5.6.2 5.7.0 5.7.1 5.7.2 5.8.0 5.8.1 5.9.0 6.0.0 6.0.1 3.0.1 3.1.0 All 141 releases
defender-security / vendor / spomky-labs / cbor-php / src / Decoder.php

Decoder.php in Defender Security – Malware Scanner, Login Security & Firewall 6.0.1, at vendor/spomky-labs/cbor-php/src/Decoder.php

269 lines 9.5 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 declare(strict_types=1);
4
5 /*
6 * The MIT License (MIT)
7 *
8 * Copyright (c) 2018-2020 Spomky-Labs
9 *
10 * This software may be modified and distributed under the terms
11 * of the MIT license. See the LICENSE file for details.
12 */
13
14 namespace CBOR;
15
16 use CBOR\OtherObject\BreakObject;
17 use CBOR\OtherObject\DoublePrecisionFloatObject;
18 use CBOR\OtherObject\FalseObject;
19 use CBOR\OtherObject\HalfPrecisionFloatObject;
20 use CBOR\OtherObject\NullObject;
21 use CBOR\OtherObject\OtherObjectManager;
22 use CBOR\OtherObject\OtherObjectManagerInterface;
23 use CBOR\OtherObject\SimpleObject;
24 use CBOR\OtherObject\SinglePrecisionFloatObject;
25 use CBOR\OtherObject\TrueObject;
26 use CBOR\OtherObject\UndefinedObject;
27 use CBOR\Tag\Base16EncodingTag;
28 use CBOR\Tag\Base64EncodingTag;
29 use CBOR\Tag\Base64Tag;
30 use CBOR\Tag\Base64UrlEncodingTag;
31 use CBOR\Tag\Base64UrlTag;
32 use CBOR\Tag\BigFloatTag;
33 use CBOR\Tag\CBOREncodingTag;
34 use CBOR\Tag\CBORTag;
35 use CBOR\Tag\DatetimeTag;
36 use CBOR\Tag\DecimalFractionTag;
37 use CBOR\Tag\MimeTag;
38 use CBOR\Tag\NegativeBigIntegerTag;
39 use CBOR\Tag\TagManager;
40 use CBOR\Tag\TagManagerInterface;
41 use CBOR\Tag\TimestampTag;
42 use CBOR\Tag\UnsignedBigIntegerTag;
43 use CBOR\Tag\UriTag;
44 use InvalidArgumentException;
45 use function ord;
46 use RuntimeException;
47 use const STR_PAD_LEFT;
48
49 final class Decoder implements DecoderInterface
50 {
51 /**
52 * @var Tag\TagManagerInterface
53 */
54 private $tagManager;
55
56 /**
57 * @var OtherObject\OtherObjectManagerInterface
58 */
59 private $otherObjectManager;
60
61 public function __construct(
62 ?TagManagerInterface $tagManager = null,
63 ?OtherObjectManagerInterface $otherTypeManager = null
64 ) {
65 $this->tagManager = $tagManager ?? $this->generateTagManager();
66 $this->otherObjectManager = $otherTypeManager ?? $this->generateOtherObjectManager();
67 }
68
69 public static function create(
70 ?TagManagerInterface $tagManager = null,
71 ?OtherObjectManagerInterface $otherObjectManager = null
72 ): self {
73 return new self($tagManager, $otherObjectManager);
74 }
75
76 public function withTagManager(TagManagerInterface $tagManager): self
77 {
78 $this->tagManager = $tagManager;
79
80 return $this;
81 }
82
83 public function withOtherObjectManager(OtherObjectManagerInterface $otherObjectManager): self
84 {
85 $this->otherObjectManager = $otherObjectManager;
86
87 return $this;
88 }
89
90 public function decode(Stream $stream): CBORObject
91 {
92 return $this->process($stream, false);
93 }
94
95 private function process(Stream $stream, bool $breakable): CBORObject
96 {
97 $ib = ord($stream->read(1));
98 $mt = $ib >> 5;
99 $ai = $ib & 0b00011111;
100 $val = null;
101 switch ($ai) {
102 case CBORObject::LENGTH_1_BYTE: //24
103 case CBORObject::LENGTH_2_BYTES: //25
104 case CBORObject::LENGTH_4_BYTES: //26
105 case CBORObject::LENGTH_8_BYTES: //27
106 $val = $stream->read(2 ** ($ai & 0b00000111));
107 break;
108 case CBORObject::FUTURE_USE_1: //28
109 case CBORObject::FUTURE_USE_2: //29
110 case CBORObject::FUTURE_USE_3: //30
111 throw new InvalidArgumentException(sprintf(
112 'Cannot parse the data. Found invalid Additional Information "%s" (%d).',
113 str_pad(decbin($ai), 8, '0', STR_PAD_LEFT),
114 $ai
115 ));
116 case CBORObject::LENGTH_INDEFINITE: //31
117 return $this->processInfinite($stream, $mt, $breakable);
118 }
119
120 return $this->processFinite($stream, $mt, $ai, $val);
121 }
122
123 private function processFinite(Stream $stream, int $mt, int $ai, ?string $val): CBORObject
124 {
125 switch ($mt) {
126 case CBORObject::MAJOR_TYPE_UNSIGNED_INTEGER: //0
127 return UnsignedIntegerObject::createObjectForValue($ai, $val);
128 case CBORObject::MAJOR_TYPE_NEGATIVE_INTEGER: //1
129 return NegativeIntegerObject::createObjectForValue($ai, $val);
130 case CBORObject::MAJOR_TYPE_BYTE_STRING: //2
131 $length = $val === null ? $ai : Utils::binToInt($val);
132
133 return ByteStringObject::create($stream->read($length));
134 case CBORObject::MAJOR_TYPE_TEXT_STRING: //3
135 $length = $val === null ? $ai : Utils::binToInt($val);
136
137 return TextStringObject::create($stream->read($length));
138 case CBORObject::MAJOR_TYPE_LIST: //4
139 $object = ListObject::create();
140 $nbItems = $val === null ? $ai : Utils::binToInt($val);
141 for ($i = 0; $i < $nbItems; ++$i) {
142 $object->add($this->process($stream, false));
143 }
144
145 return $object;
146 case CBORObject::MAJOR_TYPE_MAP: //5
147 $object = MapObject::create();
148 $nbItems = $val === null ? $ai : Utils::binToInt($val);
149 for ($i = 0; $i < $nbItems; ++$i) {
150 $object->add($this->process($stream, false), $this->process($stream, false));
151 }
152
153 return $object;
154 case CBORObject::MAJOR_TYPE_TAG: //6
155 return $this->tagManager->createObjectForValue($ai, $val, $this->process($stream, false));
156 case CBORObject::MAJOR_TYPE_OTHER_TYPE: //7
157 return $this->otherObjectManager->createObjectForValue($ai, $val);
158 default:
159 throw new RuntimeException(sprintf(
160 'Unsupported major type "%s" (%d).',
161 str_pad(decbin($mt), 5, '0', STR_PAD_LEFT),
162 $mt
163 )); // Should never append
164 }
165 }
166
167 private function processInfinite(Stream $stream, int $mt, bool $breakable): CBORObject
168 {
169 switch ($mt) {
170 case CBORObject::MAJOR_TYPE_BYTE_STRING: //2
171 $object = IndefiniteLengthByteStringObject::create();
172 while (! ($it = $this->process($stream, true)) instanceof BreakObject) {
173 if (! $it instanceof ByteStringObject) {
174 throw new RuntimeException(
175 'Unable to parse the data. Infinite Byte String object can only get Byte String objects.'
176 );
177 }
178 $object->add($it);
179 }
180
181 return $object;
182 case CBORObject::MAJOR_TYPE_TEXT_STRING: //3
183 $object = IndefiniteLengthTextStringObject::create();
184 while (! ($it = $this->process($stream, true)) instanceof BreakObject) {
185 if (! $it instanceof TextStringObject) {
186 throw new RuntimeException(
187 'Unable to parse the data. Infinite Text String object can only get Text String objects.'
188 );
189 }
190 $object->add($it);
191 }
192
193 return $object;
194 case CBORObject::MAJOR_TYPE_LIST: //4
195 $object = IndefiniteLengthListObject::create();
196 $it = $this->process($stream, true);
197 while (! $it instanceof BreakObject) {
198 $object->add($it);
199 $it = $this->process($stream, true);
200 }
201
202 return $object;
203 case CBORObject::MAJOR_TYPE_MAP: //5
204 $object = IndefiniteLengthMapObject::create();
205 while (! ($it = $this->process($stream, true)) instanceof BreakObject) {
206 $object->add($it, $this->process($stream, false));
207 }
208
209 return $object;
210 case CBORObject::MAJOR_TYPE_OTHER_TYPE: //7
211 if (! $breakable) {
212 throw new InvalidArgumentException('Cannot parse the data. No enclosing indefinite.');
213 }
214
215 return BreakObject::create();
216 case CBORObject::MAJOR_TYPE_UNSIGNED_INTEGER: //0
217 case CBORObject::MAJOR_TYPE_NEGATIVE_INTEGER: //1
218 case CBORObject::MAJOR_TYPE_TAG: //6
219 default:
220 throw new InvalidArgumentException(sprintf(
221 'Cannot parse the data. Found infinite length for Major Type "%s" (%d).',
222 str_pad(decbin($mt), 5, '0', STR_PAD_LEFT),
223 $mt
224 ));
225 }
226 }
227
228 private function generateTagManager(): TagManagerInterface
229 {
230 return TagManager::create()
231 ->add(DatetimeTag::class)
232 ->add(TimestampTag::class)
233
234 ->add(UnsignedBigIntegerTag::class)
235 ->add(NegativeBigIntegerTag::class)
236
237 ->add(DecimalFractionTag::class)
238 ->add(BigFloatTag::class)
239
240 ->add(Base64UrlEncodingTag::class)
241 ->add(Base64EncodingTag::class)
242 ->add(Base16EncodingTag::class)
243 ->add(CBOREncodingTag::class)
244
245 ->add(UriTag::class)
246 ->add(Base64UrlTag::class)
247 ->add(Base64Tag::class)
248 ->add(MimeTag::class)
249
250 ->add(CBORTag::class)
251 ;
252 }
253
254 private function generateOtherObjectManager(): OtherObjectManagerInterface
255 {
256 return OtherObjectManager::create()
257 ->add(BreakObject::class)
258 ->add(SimpleObject::class)
259 ->add(FalseObject::class)
260 ->add(TrueObject::class)
261 ->add(NullObject::class)
262 ->add(UndefinedObject::class)
263 ->add(HalfPrecisionFloatObject::class)
264 ->add(SinglePrecisionFloatObject::class)
265 ->add(DoublePrecisionFloatObject::class)
266 ;
267 }
268 }
269