a geicko-2 based round robin ranking system designed to test c++ battleship submissions battleship.dunkirk.sh
at main 21 kB view raw
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 5package ssh 6 7import ( 8 "bytes" 9 "encoding/binary" 10 "errors" 11 "fmt" 12 "io" 13 "math/big" 14 "reflect" 15 "strconv" 16 "strings" 17) 18 19// These are SSH message type numbers. They are scattered around several 20// documents but many were taken from [SSH-PARAMETERS]. 21const ( 22 msgIgnore = 2 23 msgUnimplemented = 3 24 msgDebug = 4 25 msgNewKeys = 21 26) 27 28// SSH messages: 29// 30// These structures mirror the wire format of the corresponding SSH messages. 31// They are marshaled using reflection with the marshal and unmarshal functions 32// in this file. The only wrinkle is that a final member of type []byte with a 33// ssh tag of "rest" receives the remainder of a packet when unmarshaling. 34 35// See RFC 4253, section 11.1. 36const msgDisconnect = 1 37 38// disconnectMsg is the message that signals a disconnect. It is also 39// the error type returned from mux.Wait() 40type disconnectMsg struct { 41 Reason uint32 `sshtype:"1"` 42 Message string 43 Language string 44} 45 46func (d *disconnectMsg) Error() string { 47 return fmt.Sprintf("ssh: disconnect, reason %d: %s", d.Reason, d.Message) 48} 49 50// See RFC 4253, section 7.1. 51const msgKexInit = 20 52 53type kexInitMsg struct { 54 Cookie [16]byte `sshtype:"20"` 55 KexAlgos []string 56 ServerHostKeyAlgos []string 57 CiphersClientServer []string 58 CiphersServerClient []string 59 MACsClientServer []string 60 MACsServerClient []string 61 CompressionClientServer []string 62 CompressionServerClient []string 63 LanguagesClientServer []string 64 LanguagesServerClient []string 65 FirstKexFollows bool 66 Reserved uint32 67} 68 69// See RFC 4253, section 8. 70 71// Diffie-Hellman 72const msgKexDHInit = 30 73 74type kexDHInitMsg struct { 75 X *big.Int `sshtype:"30"` 76} 77 78const msgKexECDHInit = 30 79 80type kexECDHInitMsg struct { 81 ClientPubKey []byte `sshtype:"30"` 82} 83 84const msgKexECDHReply = 31 85 86type kexECDHReplyMsg struct { 87 HostKey []byte `sshtype:"31"` 88 EphemeralPubKey []byte 89 Signature []byte 90} 91 92const msgKexDHReply = 31 93 94type kexDHReplyMsg struct { 95 HostKey []byte `sshtype:"31"` 96 Y *big.Int 97 Signature []byte 98} 99 100// See RFC 4419, section 5. 101const msgKexDHGexGroup = 31 102 103type kexDHGexGroupMsg struct { 104 P *big.Int `sshtype:"31"` 105 G *big.Int 106} 107 108const msgKexDHGexInit = 32 109 110type kexDHGexInitMsg struct { 111 X *big.Int `sshtype:"32"` 112} 113 114const msgKexDHGexReply = 33 115 116type kexDHGexReplyMsg struct { 117 HostKey []byte `sshtype:"33"` 118 Y *big.Int 119 Signature []byte 120} 121 122const msgKexDHGexRequest = 34 123 124type kexDHGexRequestMsg struct { 125 MinBits uint32 `sshtype:"34"` 126 PreferredBits uint32 127 MaxBits uint32 128} 129 130// See RFC 4253, section 10. 131const msgServiceRequest = 5 132 133type serviceRequestMsg struct { 134 Service string `sshtype:"5"` 135} 136 137// See RFC 4253, section 10. 138const msgServiceAccept = 6 139 140type serviceAcceptMsg struct { 141 Service string `sshtype:"6"` 142} 143 144// See RFC 8308, section 2.3 145const msgExtInfo = 7 146 147type extInfoMsg struct { 148 NumExtensions uint32 `sshtype:"7"` 149 Payload []byte `ssh:"rest"` 150} 151 152// See RFC 4252, section 5. 153const msgUserAuthRequest = 50 154 155type userAuthRequestMsg struct { 156 User string `sshtype:"50"` 157 Service string 158 Method string 159 Payload []byte `ssh:"rest"` 160} 161 162// Used for debug printouts of packets. 163type userAuthSuccessMsg struct { 164} 165 166// See RFC 4252, section 5.1 167const msgUserAuthFailure = 51 168 169type userAuthFailureMsg struct { 170 Methods []string `sshtype:"51"` 171 PartialSuccess bool 172} 173 174// See RFC 4252, section 5.1 175const msgUserAuthSuccess = 52 176 177// See RFC 4252, section 5.4 178const msgUserAuthBanner = 53 179 180type userAuthBannerMsg struct { 181 Message string `sshtype:"53"` 182 // unused, but required to allow message parsing 183 Language string 184} 185 186// See RFC 4256, section 3.2 187const msgUserAuthInfoRequest = 60 188const msgUserAuthInfoResponse = 61 189 190type userAuthInfoRequestMsg struct { 191 Name string `sshtype:"60"` 192 Instruction string 193 Language string 194 NumPrompts uint32 195 Prompts []byte `ssh:"rest"` 196} 197 198// See RFC 4254, section 5.1. 199const msgChannelOpen = 90 200 201type channelOpenMsg struct { 202 ChanType string `sshtype:"90"` 203 PeersID uint32 204 PeersWindow uint32 205 MaxPacketSize uint32 206 TypeSpecificData []byte `ssh:"rest"` 207} 208 209const msgChannelExtendedData = 95 210const msgChannelData = 94 211 212// Used for debug print outs of packets. 213type channelDataMsg struct { 214 PeersID uint32 `sshtype:"94"` 215 Length uint32 216 Rest []byte `ssh:"rest"` 217} 218 219// See RFC 4254, section 5.1. 220const msgChannelOpenConfirm = 91 221 222type channelOpenConfirmMsg struct { 223 PeersID uint32 `sshtype:"91"` 224 MyID uint32 225 MyWindow uint32 226 MaxPacketSize uint32 227 TypeSpecificData []byte `ssh:"rest"` 228} 229 230// See RFC 4254, section 5.1. 231const msgChannelOpenFailure = 92 232 233type channelOpenFailureMsg struct { 234 PeersID uint32 `sshtype:"92"` 235 Reason RejectionReason 236 Message string 237 Language string 238} 239 240const msgChannelRequest = 98 241 242type channelRequestMsg struct { 243 PeersID uint32 `sshtype:"98"` 244 Request string 245 WantReply bool 246 RequestSpecificData []byte `ssh:"rest"` 247} 248 249// See RFC 4254, section 5.4. 250const msgChannelSuccess = 99 251 252type channelRequestSuccessMsg struct { 253 PeersID uint32 `sshtype:"99"` 254} 255 256// See RFC 4254, section 5.4. 257const msgChannelFailure = 100 258 259type channelRequestFailureMsg struct { 260 PeersID uint32 `sshtype:"100"` 261} 262 263// See RFC 4254, section 5.3 264const msgChannelClose = 97 265 266type channelCloseMsg struct { 267 PeersID uint32 `sshtype:"97"` 268} 269 270// See RFC 4254, section 5.3 271const msgChannelEOF = 96 272 273type channelEOFMsg struct { 274 PeersID uint32 `sshtype:"96"` 275} 276 277// See RFC 4254, section 4 278const msgGlobalRequest = 80 279 280type globalRequestMsg struct { 281 Type string `sshtype:"80"` 282 WantReply bool 283 Data []byte `ssh:"rest"` 284} 285 286// See RFC 4254, section 4 287const msgRequestSuccess = 81 288 289type globalRequestSuccessMsg struct { 290 Data []byte `ssh:"rest" sshtype:"81"` 291} 292 293// See RFC 4254, section 4 294const msgRequestFailure = 82 295 296type globalRequestFailureMsg struct { 297 Data []byte `ssh:"rest" sshtype:"82"` 298} 299 300// See RFC 4254, section 5.2 301const msgChannelWindowAdjust = 93 302 303type windowAdjustMsg struct { 304 PeersID uint32 `sshtype:"93"` 305 AdditionalBytes uint32 306} 307 308// See RFC 4252, section 7 309const msgUserAuthPubKeyOk = 60 310 311type userAuthPubKeyOkMsg struct { 312 Algo string `sshtype:"60"` 313 PubKey []byte 314} 315 316// See RFC 4462, section 3 317const msgUserAuthGSSAPIResponse = 60 318 319type userAuthGSSAPIResponse struct { 320 SupportMech []byte `sshtype:"60"` 321} 322 323const msgUserAuthGSSAPIToken = 61 324 325type userAuthGSSAPIToken struct { 326 Token []byte `sshtype:"61"` 327} 328 329const msgUserAuthGSSAPIMIC = 66 330 331type userAuthGSSAPIMIC struct { 332 MIC []byte `sshtype:"66"` 333} 334 335// See RFC 4462, section 3.9 336const msgUserAuthGSSAPIErrTok = 64 337 338type userAuthGSSAPIErrTok struct { 339 ErrorToken []byte `sshtype:"64"` 340} 341 342// See RFC 4462, section 3.8 343const msgUserAuthGSSAPIError = 65 344 345type userAuthGSSAPIError struct { 346 MajorStatus uint32 `sshtype:"65"` 347 MinorStatus uint32 348 Message string 349 LanguageTag string 350} 351 352// Transport layer OpenSSH extension. See [PROTOCOL], section 1.9 353const msgPing = 192 354 355type pingMsg struct { 356 Data string `sshtype:"192"` 357} 358 359// Transport layer OpenSSH extension. See [PROTOCOL], section 1.9 360const msgPong = 193 361 362type pongMsg struct { 363 Data string `sshtype:"193"` 364} 365 366// typeTags returns the possible type bytes for the given reflect.Type, which 367// should be a struct. The possible values are separated by a '|' character. 368func typeTags(structType reflect.Type) (tags []byte) { 369 tagStr := structType.Field(0).Tag.Get("sshtype") 370 371 for _, tag := range strings.Split(tagStr, "|") { 372 i, err := strconv.Atoi(tag) 373 if err == nil { 374 tags = append(tags, byte(i)) 375 } 376 } 377 378 return tags 379} 380 381func fieldError(t reflect.Type, field int, problem string) error { 382 if problem != "" { 383 problem = ": " + problem 384 } 385 return fmt.Errorf("ssh: unmarshal error for field %s of type %s%s", t.Field(field).Name, t.Name(), problem) 386} 387 388var errShortRead = errors.New("ssh: short read") 389 390// Unmarshal parses data in SSH wire format into a structure. The out 391// argument should be a pointer to struct. If the first member of the 392// struct has the "sshtype" tag set to a '|'-separated set of numbers 393// in decimal, the packet must start with one of those numbers. In 394// case of error, Unmarshal returns a ParseError or 395// UnexpectedMessageError. 396func Unmarshal(data []byte, out interface{}) error { 397 v := reflect.ValueOf(out).Elem() 398 structType := v.Type() 399 expectedTypes := typeTags(structType) 400 401 var expectedType byte 402 if len(expectedTypes) > 0 { 403 expectedType = expectedTypes[0] 404 } 405 406 if len(data) == 0 { 407 return parseError(expectedType) 408 } 409 410 if len(expectedTypes) > 0 { 411 goodType := false 412 for _, e := range expectedTypes { 413 if e > 0 && data[0] == e { 414 goodType = true 415 break 416 } 417 } 418 if !goodType { 419 return fmt.Errorf("ssh: unexpected message type %d (expected one of %v)", data[0], expectedTypes) 420 } 421 data = data[1:] 422 } 423 424 var ok bool 425 for i := 0; i < v.NumField(); i++ { 426 field := v.Field(i) 427 t := field.Type() 428 switch t.Kind() { 429 case reflect.Bool: 430 if len(data) < 1 { 431 return errShortRead 432 } 433 field.SetBool(data[0] != 0) 434 data = data[1:] 435 case reflect.Array: 436 if t.Elem().Kind() != reflect.Uint8 { 437 return fieldError(structType, i, "array of unsupported type") 438 } 439 if len(data) < t.Len() { 440 return errShortRead 441 } 442 for j, n := 0, t.Len(); j < n; j++ { 443 field.Index(j).Set(reflect.ValueOf(data[j])) 444 } 445 data = data[t.Len():] 446 case reflect.Uint64: 447 var u64 uint64 448 if u64, data, ok = parseUint64(data); !ok { 449 return errShortRead 450 } 451 field.SetUint(u64) 452 case reflect.Uint32: 453 var u32 uint32 454 if u32, data, ok = parseUint32(data); !ok { 455 return errShortRead 456 } 457 field.SetUint(uint64(u32)) 458 case reflect.Uint8: 459 if len(data) < 1 { 460 return errShortRead 461 } 462 field.SetUint(uint64(data[0])) 463 data = data[1:] 464 case reflect.String: 465 var s []byte 466 if s, data, ok = parseString(data); !ok { 467 return fieldError(structType, i, "") 468 } 469 field.SetString(string(s)) 470 case reflect.Slice: 471 switch t.Elem().Kind() { 472 case reflect.Uint8: 473 if structType.Field(i).Tag.Get("ssh") == "rest" { 474 field.Set(reflect.ValueOf(data)) 475 data = nil 476 } else { 477 var s []byte 478 if s, data, ok = parseString(data); !ok { 479 return errShortRead 480 } 481 field.Set(reflect.ValueOf(s)) 482 } 483 case reflect.String: 484 var nl []string 485 if nl, data, ok = parseNameList(data); !ok { 486 return errShortRead 487 } 488 field.Set(reflect.ValueOf(nl)) 489 default: 490 return fieldError(structType, i, "slice of unsupported type") 491 } 492 case reflect.Ptr: 493 if t == bigIntType { 494 var n *big.Int 495 if n, data, ok = parseInt(data); !ok { 496 return errShortRead 497 } 498 field.Set(reflect.ValueOf(n)) 499 } else { 500 return fieldError(structType, i, "pointer to unsupported type") 501 } 502 default: 503 return fieldError(structType, i, fmt.Sprintf("unsupported type: %v", t)) 504 } 505 } 506 507 if len(data) != 0 { 508 return parseError(expectedType) 509 } 510 511 return nil 512} 513 514// Marshal serializes the message in msg to SSH wire format. The msg 515// argument should be a struct or pointer to struct. If the first 516// member has the "sshtype" tag set to a number in decimal, that 517// number is prepended to the result. If the last of member has the 518// "ssh" tag set to "rest", its contents are appended to the output. 519func Marshal(msg interface{}) []byte { 520 out := make([]byte, 0, 64) 521 return marshalStruct(out, msg) 522} 523 524func marshalStruct(out []byte, msg interface{}) []byte { 525 v := reflect.Indirect(reflect.ValueOf(msg)) 526 msgTypes := typeTags(v.Type()) 527 if len(msgTypes) > 0 { 528 out = append(out, msgTypes[0]) 529 } 530 531 for i, n := 0, v.NumField(); i < n; i++ { 532 field := v.Field(i) 533 switch t := field.Type(); t.Kind() { 534 case reflect.Bool: 535 var v uint8 536 if field.Bool() { 537 v = 1 538 } 539 out = append(out, v) 540 case reflect.Array: 541 if t.Elem().Kind() != reflect.Uint8 { 542 panic(fmt.Sprintf("array of non-uint8 in field %d: %T", i, field.Interface())) 543 } 544 for j, l := 0, t.Len(); j < l; j++ { 545 out = append(out, uint8(field.Index(j).Uint())) 546 } 547 case reflect.Uint32: 548 out = appendU32(out, uint32(field.Uint())) 549 case reflect.Uint64: 550 out = appendU64(out, uint64(field.Uint())) 551 case reflect.Uint8: 552 out = append(out, uint8(field.Uint())) 553 case reflect.String: 554 s := field.String() 555 out = appendInt(out, len(s)) 556 out = append(out, s...) 557 case reflect.Slice: 558 switch t.Elem().Kind() { 559 case reflect.Uint8: 560 if v.Type().Field(i).Tag.Get("ssh") != "rest" { 561 out = appendInt(out, field.Len()) 562 } 563 out = append(out, field.Bytes()...) 564 case reflect.String: 565 offset := len(out) 566 out = appendU32(out, 0) 567 if n := field.Len(); n > 0 { 568 for j := 0; j < n; j++ { 569 f := field.Index(j) 570 if j != 0 { 571 out = append(out, ',') 572 } 573 out = append(out, f.String()...) 574 } 575 // overwrite length value 576 binary.BigEndian.PutUint32(out[offset:], uint32(len(out)-offset-4)) 577 } 578 default: 579 panic(fmt.Sprintf("slice of unknown type in field %d: %T", i, field.Interface())) 580 } 581 case reflect.Ptr: 582 if t == bigIntType { 583 var n *big.Int 584 nValue := reflect.ValueOf(&n) 585 nValue.Elem().Set(field) 586 needed := intLength(n) 587 oldLength := len(out) 588 589 if cap(out)-len(out) < needed { 590 newOut := make([]byte, len(out), 2*(len(out)+needed)) 591 copy(newOut, out) 592 out = newOut 593 } 594 out = out[:oldLength+needed] 595 marshalInt(out[oldLength:], n) 596 } else { 597 panic(fmt.Sprintf("pointer to unknown type in field %d: %T", i, field.Interface())) 598 } 599 } 600 } 601 602 return out 603} 604 605var bigOne = big.NewInt(1) 606 607func parseString(in []byte) (out, rest []byte, ok bool) { 608 if len(in) < 4 { 609 return 610 } 611 length := binary.BigEndian.Uint32(in) 612 in = in[4:] 613 if uint32(len(in)) < length { 614 return 615 } 616 out = in[:length] 617 rest = in[length:] 618 ok = true 619 return 620} 621 622var ( 623 comma = []byte{','} 624 emptyNameList = []string{} 625) 626 627func parseNameList(in []byte) (out []string, rest []byte, ok bool) { 628 contents, rest, ok := parseString(in) 629 if !ok { 630 return 631 } 632 if len(contents) == 0 { 633 out = emptyNameList 634 return 635 } 636 parts := bytes.Split(contents, comma) 637 out = make([]string, len(parts)) 638 for i, part := range parts { 639 out[i] = string(part) 640 } 641 return 642} 643 644func parseInt(in []byte) (out *big.Int, rest []byte, ok bool) { 645 contents, rest, ok := parseString(in) 646 if !ok { 647 return 648 } 649 out = new(big.Int) 650 651 if len(contents) > 0 && contents[0]&0x80 == 0x80 { 652 // This is a negative number 653 notBytes := make([]byte, len(contents)) 654 for i := range notBytes { 655 notBytes[i] = ^contents[i] 656 } 657 out.SetBytes(notBytes) 658 out.Add(out, bigOne) 659 out.Neg(out) 660 } else { 661 // Positive number 662 out.SetBytes(contents) 663 } 664 ok = true 665 return 666} 667 668func parseUint32(in []byte) (uint32, []byte, bool) { 669 if len(in) < 4 { 670 return 0, nil, false 671 } 672 return binary.BigEndian.Uint32(in), in[4:], true 673} 674 675func parseUint64(in []byte) (uint64, []byte, bool) { 676 if len(in) < 8 { 677 return 0, nil, false 678 } 679 return binary.BigEndian.Uint64(in), in[8:], true 680} 681 682func intLength(n *big.Int) int { 683 length := 4 /* length bytes */ 684 if n.Sign() < 0 { 685 nMinus1 := new(big.Int).Neg(n) 686 nMinus1.Sub(nMinus1, bigOne) 687 bitLen := nMinus1.BitLen() 688 if bitLen%8 == 0 { 689 // The number will need 0xff padding 690 length++ 691 } 692 length += (bitLen + 7) / 8 693 } else if n.Sign() == 0 { 694 // A zero is the zero length string 695 } else { 696 bitLen := n.BitLen() 697 if bitLen%8 == 0 { 698 // The number will need 0x00 padding 699 length++ 700 } 701 length += (bitLen + 7) / 8 702 } 703 704 return length 705} 706 707func marshalUint32(to []byte, n uint32) []byte { 708 binary.BigEndian.PutUint32(to, n) 709 return to[4:] 710} 711 712func marshalUint64(to []byte, n uint64) []byte { 713 binary.BigEndian.PutUint64(to, n) 714 return to[8:] 715} 716 717func marshalInt(to []byte, n *big.Int) []byte { 718 lengthBytes := to 719 to = to[4:] 720 length := 0 721 722 if n.Sign() < 0 { 723 // A negative number has to be converted to two's-complement 724 // form. So we'll subtract 1 and invert. If the 725 // most-significant-bit isn't set then we'll need to pad the 726 // beginning with 0xff in order to keep the number negative. 727 nMinus1 := new(big.Int).Neg(n) 728 nMinus1.Sub(nMinus1, bigOne) 729 bytes := nMinus1.Bytes() 730 for i := range bytes { 731 bytes[i] ^= 0xff 732 } 733 if len(bytes) == 0 || bytes[0]&0x80 == 0 { 734 to[0] = 0xff 735 to = to[1:] 736 length++ 737 } 738 nBytes := copy(to, bytes) 739 to = to[nBytes:] 740 length += nBytes 741 } else if n.Sign() == 0 { 742 // A zero is the zero length string 743 } else { 744 bytes := n.Bytes() 745 if len(bytes) > 0 && bytes[0]&0x80 != 0 { 746 // We'll have to pad this with a 0x00 in order to 747 // stop it looking like a negative number. 748 to[0] = 0 749 to = to[1:] 750 length++ 751 } 752 nBytes := copy(to, bytes) 753 to = to[nBytes:] 754 length += nBytes 755 } 756 757 lengthBytes[0] = byte(length >> 24) 758 lengthBytes[1] = byte(length >> 16) 759 lengthBytes[2] = byte(length >> 8) 760 lengthBytes[3] = byte(length) 761 return to 762} 763 764func writeInt(w io.Writer, n *big.Int) { 765 length := intLength(n) 766 buf := make([]byte, length) 767 marshalInt(buf, n) 768 w.Write(buf) 769} 770 771func writeString(w io.Writer, s []byte) { 772 var lengthBytes [4]byte 773 lengthBytes[0] = byte(len(s) >> 24) 774 lengthBytes[1] = byte(len(s) >> 16) 775 lengthBytes[2] = byte(len(s) >> 8) 776 lengthBytes[3] = byte(len(s)) 777 w.Write(lengthBytes[:]) 778 w.Write(s) 779} 780 781func stringLength(n int) int { 782 return 4 + n 783} 784 785func marshalString(to []byte, s []byte) []byte { 786 to[0] = byte(len(s) >> 24) 787 to[1] = byte(len(s) >> 16) 788 to[2] = byte(len(s) >> 8) 789 to[3] = byte(len(s)) 790 to = to[4:] 791 copy(to, s) 792 return to[len(s):] 793} 794 795var bigIntType = reflect.TypeOf((*big.Int)(nil)) 796 797// Decode a packet into its corresponding message. 798func decode(packet []byte) (interface{}, error) { 799 var msg interface{} 800 switch packet[0] { 801 case msgDisconnect: 802 msg = new(disconnectMsg) 803 case msgServiceRequest: 804 msg = new(serviceRequestMsg) 805 case msgServiceAccept: 806 msg = new(serviceAcceptMsg) 807 case msgExtInfo: 808 msg = new(extInfoMsg) 809 case msgKexInit: 810 msg = new(kexInitMsg) 811 case msgKexDHInit: 812 msg = new(kexDHInitMsg) 813 case msgKexDHReply: 814 msg = new(kexDHReplyMsg) 815 case msgUserAuthRequest: 816 msg = new(userAuthRequestMsg) 817 case msgUserAuthSuccess: 818 return new(userAuthSuccessMsg), nil 819 case msgUserAuthFailure: 820 msg = new(userAuthFailureMsg) 821 case msgUserAuthBanner: 822 msg = new(userAuthBannerMsg) 823 case msgUserAuthPubKeyOk: 824 msg = new(userAuthPubKeyOkMsg) 825 case msgGlobalRequest: 826 msg = new(globalRequestMsg) 827 case msgRequestSuccess: 828 msg = new(globalRequestSuccessMsg) 829 case msgRequestFailure: 830 msg = new(globalRequestFailureMsg) 831 case msgChannelOpen: 832 msg = new(channelOpenMsg) 833 case msgChannelData: 834 msg = new(channelDataMsg) 835 case msgChannelOpenConfirm: 836 msg = new(channelOpenConfirmMsg) 837 case msgChannelOpenFailure: 838 msg = new(channelOpenFailureMsg) 839 case msgChannelWindowAdjust: 840 msg = new(windowAdjustMsg) 841 case msgChannelEOF: 842 msg = new(channelEOFMsg) 843 case msgChannelClose: 844 msg = new(channelCloseMsg) 845 case msgChannelRequest: 846 msg = new(channelRequestMsg) 847 case msgChannelSuccess: 848 msg = new(channelRequestSuccessMsg) 849 case msgChannelFailure: 850 msg = new(channelRequestFailureMsg) 851 case msgUserAuthGSSAPIToken: 852 msg = new(userAuthGSSAPIToken) 853 case msgUserAuthGSSAPIMIC: 854 msg = new(userAuthGSSAPIMIC) 855 case msgUserAuthGSSAPIErrTok: 856 msg = new(userAuthGSSAPIErrTok) 857 case msgUserAuthGSSAPIError: 858 msg = new(userAuthGSSAPIError) 859 default: 860 return nil, unexpectedMessageError(0, packet[0]) 861 } 862 if err := Unmarshal(packet, msg); err != nil { 863 return nil, err 864 } 865 return msg, nil 866} 867 868var packetTypeNames = map[byte]string{ 869 msgDisconnect: "disconnectMsg", 870 msgServiceRequest: "serviceRequestMsg", 871 msgServiceAccept: "serviceAcceptMsg", 872 msgExtInfo: "extInfoMsg", 873 msgKexInit: "kexInitMsg", 874 msgKexDHInit: "kexDHInitMsg", 875 msgKexDHReply: "kexDHReplyMsg", 876 msgUserAuthRequest: "userAuthRequestMsg", 877 msgUserAuthSuccess: "userAuthSuccessMsg", 878 msgUserAuthFailure: "userAuthFailureMsg", 879 msgUserAuthPubKeyOk: "userAuthPubKeyOkMsg", 880 msgGlobalRequest: "globalRequestMsg", 881 msgRequestSuccess: "globalRequestSuccessMsg", 882 msgRequestFailure: "globalRequestFailureMsg", 883 msgChannelOpen: "channelOpenMsg", 884 msgChannelData: "channelDataMsg", 885 msgChannelOpenConfirm: "channelOpenConfirmMsg", 886 msgChannelOpenFailure: "channelOpenFailureMsg", 887 msgChannelWindowAdjust: "windowAdjustMsg", 888 msgChannelEOF: "channelEOFMsg", 889 msgChannelClose: "channelCloseMsg", 890 msgChannelRequest: "channelRequestMsg", 891 msgChannelSuccess: "channelRequestSuccessMsg", 892 msgChannelFailure: "channelRequestFailureMsg", 893}