1// Copyright 2011 The Go Authors. All rights reserved. 2// Use of this source code is governed by a BSD-style 3// license that can be found in the LICENSE file. 4 5// Package packet implements parsing and serialization of OpenPGP packets, as 6// specified in RFC 4880. 7package packet // import "golang.org/x/crypto/openpgp/packet" 8 9import ( 10 "bufio" 11 "crypto/aes" 12 "crypto/cipher" 13 "crypto/des" 14 "golang.org/x/crypto/cast5" 15 "golang.org/x/crypto/openpgp/errors" 16 "io" 17 "math/big" 18) 19 20// readFull is the same as io.ReadFull except that reading zero bytes returns 21// ErrUnexpectedEOF rather than EOF. 22func readFull(r io.Reader, buf []byte) (n int, err error) { 23 n, err = io.ReadFull(r, buf) 24 if err == io.EOF { 25 err = io.ErrUnexpectedEOF 26 } 27 return 28} 29 30// readLength reads an OpenPGP length from r. See RFC 4880, section 4.2.2. 31func readLength(r io.Reader) (length int64, isPartial bool, err error) { 32 var buf [4]byte 33 _, err = readFull(r, buf[:1]) 34 if err != nil { 35 return 36 } 37 switch { 38 case buf[0] < 192: 39 length = int64(buf[0]) 40 case buf[0] < 224: 41 length = int64(buf[0]-192) << 8 42 _, err = readFull(r, buf[0:1]) 43 if err != nil { 44 return 45 } 46 length += int64(buf[0]) + 192 47 case buf[0] < 255: 48 length = int64(1) << (buf[0] & 0x1f) 49 isPartial = true 50 default: 51 _, err = readFull(r, buf[0:4]) 52 if err != nil { 53 return 54 } 55 length = int64(buf[0])<<24 | 56 int64(buf[1])<<16 | 57 int64(buf[2])<<8 | 58 int64(buf[3]) 59 } 60 return 61} 62 63// partialLengthReader wraps an io.Reader and handles OpenPGP partial lengths. 64// The continuation lengths are parsed and removed from the stream and EOF is 65// returned at the end of the packet. See RFC 4880, section 4.2.2.4. 66type partialLengthReader struct { 67 r io.Reader 68 remaining int64 69 isPartial bool 70} 71 72func (r *partialLengthReader) Read(p []byte) (n int, err error) { 73 for r.remaining == 0 { 74 if !r.isPartial { 75 return 0, io.EOF 76 } 77 r.remaining, r.isPartial, err = readLength(r.r) 78 if err != nil { 79 return 0, err 80 } 81 } 82 83 toRead := int64(len(p)) 84 if toRead > r.remaining { 85 toRead = r.remaining 86 } 87 88 n, err = r.r.Read(p[:int(toRead)]) 89 r.remaining -= int64(n) 90 if n < int(toRead) && err == io.EOF { 91 err = io.ErrUnexpectedEOF 92 } 93 return 94} 95 96// partialLengthWriter writes a stream of data using OpenPGP partial lengths. 97// See RFC 4880, section 4.2.2.4. 98type partialLengthWriter struct { 99 w io.WriteCloser 100 lengthByte [1]byte 101} 102 103func (w *partialLengthWriter) Write(p []byte) (n int, err error) { 104 for len(p) > 0 { 105 for power := uint(14); power < 32; power-- { 106 l := 1 << power 107 if len(p) >= l { 108 w.lengthByte[0] = 224 + uint8(power) 109 _, err = w.w.Write(w.lengthByte[:]) 110 if err != nil { 111 return 112 } 113 var m int 114 m, err = w.w.Write(p[:l]) 115 n += m 116 if err != nil { 117 return 118 } 119 p = p[l:] 120 break 121 } 122 } 123 } 124 return 125} 126 127func (w *partialLengthWriter) Close() error { 128 w.lengthByte[0] = 0 129 _, err := w.w.Write(w.lengthByte[:]) 130 if err != nil { 131 return err 132 } 133 return w.w.Close() 134} 135 136// A spanReader is an io.LimitReader, but it returns ErrUnexpectedEOF if the 137// underlying Reader returns EOF before the limit has been reached. 138type spanReader struct { 139 r io.Reader 140 n int64 141} 142 143func (l *spanReader) Read(p []byte) (n int, err error) { 144 if l.n <= 0 { 145 return 0, io.EOF 146 } 147 if int64(len(p)) > l.n { 148 p = p[0:l.n] 149 } 150 n, err = l.r.Read(p) 151 l.n -= int64(n) 152 if l.n > 0 && err == io.EOF { 153 err = io.ErrUnexpectedEOF 154 } 155 return 156} 157 158// readHeader parses a packet header and returns an io.Reader which will return 159// the contents of the packet. See RFC 4880, section 4.2. 160func readHeader(r io.Reader) (tag packetType, length int64, contents io.Reader, err error) { 161 var buf [4]byte 162 _, err = io.ReadFull(r, buf[:1]) 163 if err != nil { 164 return 165 } 166 if buf[0]&0x80 == 0 { 167 err = errors.StructuralError("tag byte does not have MSB set") 168 return 169 } 170 if buf[0]&0x40 == 0 { 171 // Old format packet 172 tag = packetType((buf[0] & 0x3f) >> 2) 173 lengthType := buf[0] & 3 174 if lengthType == 3 { 175 length = -1 176 contents = r 177 return 178 } 179 lengthBytes := 1 << lengthType 180 _, err = readFull(r, buf[0:lengthBytes]) 181 if err != nil { 182 return 183 } 184 for i := 0; i < lengthBytes; i++ { 185 length <<= 8 186 length |= int64(buf[i]) 187 } 188 contents = &spanReader{r, length} 189 return 190 } 191 192 // New format packet 193 tag = packetType(buf[0] & 0x3f) 194 length, isPartial, err := readLength(r) 195 if err != nil { 196 return 197 } 198 if isPartial { 199 contents = &partialLengthReader{ 200 remaining: length, 201 isPartial: true, 202 r: r, 203 } 204 length = -1 205 } else { 206 contents = &spanReader{r, length} 207 } 208 return 209} 210 211// serializeHeader writes an OpenPGP packet header to w. See RFC 4880, section 212// 4.2. 213func serializeHeader(w io.Writer, ptype packetType, length int) (err error) { 214 var buf [6]byte 215 var n int 216 217 buf[0] = 0x80 | 0x40 | byte(ptype) 218 if length < 192 { 219 buf[1] = byte(length) 220 n = 2 221 } else if length < 8384 { 222 length -= 192 223 buf[1] = 192 + byte(length>>8) 224 buf[2] = byte(length) 225 n = 3 226 } else { 227 buf[1] = 255 228 buf[2] = byte(length >> 24) 229 buf[3] = byte(length >> 16) 230 buf[4] = byte(length >> 8) 231 buf[5] = byte(length) 232 n = 6 233 } 234 235 _, err = w.Write(buf[:n]) 236 return 237} 238 239// serializeStreamHeader writes an OpenPGP packet header to w where the 240// length of the packet is unknown. It returns a io.WriteCloser which can be 241// used to write the contents of the packet. See RFC 4880, section 4.2. 242func serializeStreamHeader(w io.WriteCloser, ptype packetType) (out io.WriteCloser, err error) { 243 var buf [1]byte 244 buf[0] = 0x80 | 0x40 | byte(ptype) 245 _, err = w.Write(buf[:]) 246 if err != nil { 247 return 248 } 249 out = &partialLengthWriter{w: w} 250 return 251} 252 253// Packet represents an OpenPGP packet. Users are expected to try casting 254// instances of this interface to specific packet types. 255type Packet interface { 256 parse(io.Reader) error 257} 258 259// consumeAll reads from the given Reader until error, returning the number of 260// bytes read. 261func consumeAll(r io.Reader) (n int64, err error) { 262 var m int 263 var buf [1024]byte 264 265 for { 266 m, err = r.Read(buf[:]) 267 n += int64(m) 268 if err == io.EOF { 269 err = nil 270 return 271 } 272 if err != nil { 273 return 274 } 275 } 276} 277 278// packetType represents the numeric ids of the different OpenPGP packet types. See 279// http://www.iana.org/assignments/pgp-parameters/pgp-parameters.xhtml#pgp-parameters-2 280type packetType uint8 281 282const ( 283 packetTypeEncryptedKey packetType = 1 284 packetTypeSignature packetType = 2 285 packetTypeSymmetricKeyEncrypted packetType = 3 286 packetTypeOnePassSignature packetType = 4 287 packetTypePrivateKey packetType = 5 288 packetTypePublicKey packetType = 6 289 packetTypePrivateSubkey packetType = 7 290 packetTypeCompressed packetType = 8 291 packetTypeSymmetricallyEncrypted packetType = 9 292 packetTypeLiteralData packetType = 11 293 packetTypeUserId packetType = 13 294 packetTypePublicSubkey packetType = 14 295 packetTypeUserAttribute packetType = 17 296 packetTypeSymmetricallyEncryptedMDC packetType = 18 297) 298 299// peekVersion detects the version of a public key packet about to 300// be read. A bufio.Reader at the original position of the io.Reader 301// is returned. 302func peekVersion(r io.Reader) (bufr *bufio.Reader, ver byte, err error) { 303 bufr = bufio.NewReader(r) 304 var verBuf []byte 305 if verBuf, err = bufr.Peek(1); err != nil { 306 return 307 } 308 ver = verBuf[0] 309 return 310} 311 312// Read reads a single OpenPGP packet from the given io.Reader. If there is an 313// error parsing a packet, the whole packet is consumed from the input. 314func Read(r io.Reader) (p Packet, err error) { 315 tag, _, contents, err := readHeader(r) 316 if err != nil { 317 return 318 } 319 320 switch tag { 321 case packetTypeEncryptedKey: 322 p = new(EncryptedKey) 323 case packetTypeSignature: 324 var version byte 325 // Detect signature version 326 if contents, version, err = peekVersion(contents); err != nil { 327 return 328 } 329 if version < 4 { 330 p = new(SignatureV3) 331 } else { 332 p = new(Signature) 333 } 334 case packetTypeSymmetricKeyEncrypted: 335 p = new(SymmetricKeyEncrypted) 336 case packetTypeOnePassSignature: 337 p = new(OnePassSignature) 338 case packetTypePrivateKey, packetTypePrivateSubkey: 339 pk := new(PrivateKey) 340 if tag == packetTypePrivateSubkey { 341 pk.IsSubkey = true 342 } 343 p = pk 344 case packetTypePublicKey, packetTypePublicSubkey: 345 var version byte 346 if contents, version, err = peekVersion(contents); err != nil { 347 return 348 } 349 isSubkey := tag == packetTypePublicSubkey 350 if version < 4 { 351 p = &PublicKeyV3{IsSubkey: isSubkey} 352 } else { 353 p = &PublicKey{IsSubkey: isSubkey} 354 } 355 case packetTypeCompressed: 356 p = new(Compressed) 357 case packetTypeSymmetricallyEncrypted: 358 p = new(SymmetricallyEncrypted) 359 case packetTypeLiteralData: 360 p = new(LiteralData) 361 case packetTypeUserId: 362 p = new(UserId) 363 case packetTypeUserAttribute: 364 p = new(UserAttribute) 365 case packetTypeSymmetricallyEncryptedMDC: 366 se := new(SymmetricallyEncrypted) 367 se.MDC = true 368 p = se 369 default: 370 err = errors.UnknownPacketTypeError(tag) 371 } 372 if p != nil { 373 err = p.parse(contents) 374 } 375 if err != nil { 376 consumeAll(contents) 377 } 378 return 379} 380 381// SignatureType represents the different semantic meanings of an OpenPGP 382// signature. See RFC 4880, section 5.2.1. 383type SignatureType uint8 384 385const ( 386 SigTypeBinary SignatureType = 0 387 SigTypeText = 1 388 SigTypeGenericCert = 0x10 389 SigTypePersonaCert = 0x11 390 SigTypeCasualCert = 0x12 391 SigTypePositiveCert = 0x13 392 SigTypeSubkeyBinding = 0x18 393 SigTypePrimaryKeyBinding = 0x19 394 SigTypeDirectSignature = 0x1F 395 SigTypeKeyRevocation = 0x20 396 SigTypeSubkeyRevocation = 0x28 397) 398 399// PublicKeyAlgorithm represents the different public key system specified for 400// OpenPGP. See 401// http://www.iana.org/assignments/pgp-parameters/pgp-parameters.xhtml#pgp-parameters-12 402type PublicKeyAlgorithm uint8 403 404const ( 405 PubKeyAlgoRSA PublicKeyAlgorithm = 1 406 PubKeyAlgoRSAEncryptOnly PublicKeyAlgorithm = 2 407 PubKeyAlgoRSASignOnly PublicKeyAlgorithm = 3 408 PubKeyAlgoElGamal PublicKeyAlgorithm = 16 409 PubKeyAlgoDSA PublicKeyAlgorithm = 17 410 // RFC 6637, Section 5. 411 PubKeyAlgoECDH PublicKeyAlgorithm = 18 412 PubKeyAlgoECDSA PublicKeyAlgorithm = 19 413) 414 415// CanEncrypt returns true if it's possible to encrypt a message to a public 416// key of the given type. 417func (pka PublicKeyAlgorithm) CanEncrypt() bool { 418 switch pka { 419 case PubKeyAlgoRSA, PubKeyAlgoRSAEncryptOnly, PubKeyAlgoElGamal: 420 return true 421 } 422 return false 423} 424 425// CanSign returns true if it's possible for a public key of the given type to 426// sign a message. 427func (pka PublicKeyAlgorithm) CanSign() bool { 428 switch pka { 429 case PubKeyAlgoRSA, PubKeyAlgoRSASignOnly, PubKeyAlgoDSA, PubKeyAlgoECDSA: 430 return true 431 } 432 return false 433} 434 435// CipherFunction represents the different block ciphers specified for OpenPGP. See 436// http://www.iana.org/assignments/pgp-parameters/pgp-parameters.xhtml#pgp-parameters-13 437type CipherFunction uint8 438 439const ( 440 Cipher3DES CipherFunction = 2 441 CipherCAST5 CipherFunction = 3 442 CipherAES128 CipherFunction = 7 443 CipherAES192 CipherFunction = 8 444 CipherAES256 CipherFunction = 9 445) 446 447// KeySize returns the key size, in bytes, of cipher. 448func (cipher CipherFunction) KeySize() int { 449 switch cipher { 450 case Cipher3DES: 451 return 24 452 case CipherCAST5: 453 return cast5.KeySize 454 case CipherAES128: 455 return 16 456 case CipherAES192: 457 return 24 458 case CipherAES256: 459 return 32 460 } 461 return 0 462} 463 464// blockSize returns the block size, in bytes, of cipher. 465func (cipher CipherFunction) blockSize() int { 466 switch cipher { 467 case Cipher3DES: 468 return des.BlockSize 469 case CipherCAST5: 470 return 8 471 case CipherAES128, CipherAES192, CipherAES256: 472 return 16 473 } 474 return 0 475} 476 477// new returns a fresh instance of the given cipher. 478func (cipher CipherFunction) new(key []byte) (block cipher.Block) { 479 switch cipher { 480 case Cipher3DES: 481 block, _ = des.NewTripleDESCipher(key) 482 case CipherCAST5: 483 block, _ = cast5.NewCipher(key) 484 case CipherAES128, CipherAES192, CipherAES256: 485 block, _ = aes.NewCipher(key) 486 } 487 return 488} 489 490// readMPI reads a big integer from r. The bit length returned is the bit 491// length that was specified in r. This is preserved so that the integer can be 492// reserialized exactly. 493func readMPI(r io.Reader) (mpi []byte, bitLength uint16, err error) { 494 var buf [2]byte 495 _, err = readFull(r, buf[0:]) 496 if err != nil { 497 return 498 } 499 bitLength = uint16(buf[0])<<8 | uint16(buf[1]) 500 numBytes := (int(bitLength) + 7) / 8 501 mpi = make([]byte, numBytes) 502 _, err = readFull(r, mpi) 503 return 504} 505 506// mpiLength returns the length of the given *big.Int when serialized as an 507// MPI. 508func mpiLength(n *big.Int) (mpiLengthInBytes int) { 509 mpiLengthInBytes = 2 /* MPI length */ 510 mpiLengthInBytes += (n.BitLen() + 7) / 8 511 return 512} 513 514// writeMPI serializes a big integer to w. 515func writeMPI(w io.Writer, bitLength uint16, mpiBytes []byte) (err error) { 516 _, err = w.Write([]byte{byte(bitLength >> 8), byte(bitLength)}) 517 if err == nil { 518 _, err = w.Write(mpiBytes) 519 } 520 return 521} 522 523// writeBig serializes a *big.Int to w. 524func writeBig(w io.Writer, i *big.Int) error { 525 return writeMPI(w, uint16(i.BitLen()), i.Bytes()) 526} 527 528// CompressionAlgo Represents the different compression algorithms 529// supported by OpenPGP (except for BZIP2, which is not currently 530// supported). See Section 9.3 of RFC 4880. 531type CompressionAlgo uint8 532 533const ( 534 CompressionNone CompressionAlgo = 0 535 CompressionZIP CompressionAlgo = 1 536 CompressionZLIB CompressionAlgo = 2 537) 538