vitess.io/vitess@v0.16.2/go/mysql/binlog_dump.go (about) 1 /* 2 Copyright 2022 The Vitess Authors. 3 4 Licensed under the Apache License, Version 2.0 (the "License"); 5 you may not use this file except in compliance with the License. 6 You may obtain a copy of the License at 7 8 http://www.apache.org/licenses/LICENSE-2.0 9 10 Unless required by applicable law or agreed to in writing, software 11 distributed under the License is distributed on an "AS IS" BASIS, 12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 See the License for the specific language governing permissions and 14 limitations under the License. 15 */ 16 17 package mysql 18 19 import ( 20 "encoding/binary" 21 "io" 22 23 vtrpcpb "vitess.io/vitess/go/vt/proto/vtrpc" 24 "vitess.io/vitess/go/vt/vterrors" 25 ) 26 27 var ( 28 // BinglogMagicNumber is 4-byte number at the beginning of every binary log 29 BinglogMagicNumber = []byte{0xfe, 0x62, 0x69, 0x6e} 30 readPacketErr = vterrors.Errorf(vtrpcpb.Code_INTERNAL, "error reading BinlogDumpGTID packet") 31 ) 32 33 const ( 34 BinlogDumpNonBlock = 0x01 35 BinlogThroughPosition = 0x02 36 BinlogThroughGTID = 0x04 37 ) 38 39 func (c *Conn) parseComBinlogDump(data []byte) (logFile string, binlogPos uint32, err error) { 40 pos := 1 41 42 binlogPos, pos, ok := readUint32(data, pos) 43 if !ok { 44 return logFile, binlogPos, readPacketErr 45 } 46 47 pos += 2 // flags 48 pos += 4 // server-id 49 50 logFile = string(data[pos:]) 51 return logFile, binlogPos, nil 52 } 53 54 func (c *Conn) parseComBinlogDumpGTID(data []byte) (logFile string, logPos uint64, position Position, err error) { 55 // see https://dev.mysql.com/doc/internals/en/com-binlog-dump-gtid.html 56 pos := 1 57 58 flags2 := binary.LittleEndian.Uint16(data[pos : pos+2]) 59 pos += 2 // flags 60 pos += 4 // server-id 61 62 fileNameLen, pos, ok := readUint32(data, pos) 63 if !ok { 64 return logFile, logPos, position, readPacketErr 65 } 66 logFile = string(data[pos : pos+int(fileNameLen)]) 67 pos += int(fileNameLen) 68 69 logPos, pos, ok = readUint64(data, pos) 70 if !ok { 71 return logFile, logPos, position, readPacketErr 72 } 73 74 if flags2&BinlogDumpNonBlock != 0 { 75 return logFile, logPos, position, io.EOF 76 } 77 if flags2&BinlogThroughGTID != 0 { 78 dataSize, pos, ok := readUint32(data, pos) 79 if !ok { 80 return logFile, logPos, position, readPacketErr 81 } 82 if gtid := string(data[pos : pos+int(dataSize)]); gtid != "" { 83 position, err = DecodePosition(gtid) 84 if err != nil { 85 return logFile, logPos, position, err 86 } 87 } 88 } 89 90 return logFile, logPos, position, nil 91 }