@@ -807,12 +807,12 @@ func appendLengthEncodedInteger(b []byte, n uint64) []byte {
807
807
byte (n >> 32 ), byte (n >> 40 ), byte (n >> 48 ), byte (n >> 56 ))
808
808
}
809
809
810
- // Escape string with backslashes (\)
810
+ // escapeBytesBackslash escapes []byte with backslashes (\)
811
811
// This escapes the contents of a string (provided as []byte) by adding backslashes before special
812
812
// characters, and turning others into specific escape sequences, such as
813
813
// turning newlines into \n and null bytes into \0.
814
814
// https://github.com/mysql/mysql-server/blob/mysql-5.7.5/mysys/charset.c#L823-L932
815
- func escapeBackslash (buf , v []byte ) []byte {
815
+ func escapeBytesBackslash (buf , v []byte ) []byte {
816
816
pos := len (buf )
817
817
end := pos + len (v )* 2
818
818
if cap (buf ) < end {
@@ -861,12 +861,63 @@ func escapeBackslash(buf, v []byte) []byte {
861
861
return buf [:pos ]
862
862
}
863
863
864
- // Escape apostrophes by doubling them up
864
+ // escapeStringBackslash is similar to escapeBytesBackslash but for string.
865
+ func escapeStringBackslash (buf []byte , v string ) []byte {
866
+ pos := len (buf )
867
+ end := pos + len (v )* 2
868
+ if cap (buf ) < end {
869
+ n := make ([]byte , pos + end )
870
+ copy (n , buf )
871
+ buf = n
872
+ }
873
+ buf = buf [0 :end ]
874
+
875
+ for i := 0 ; i < len (v ); i ++ {
876
+ c := v [i ]
877
+ switch c {
878
+ case '\x00' :
879
+ buf [pos ] = '\\'
880
+ buf [pos + 1 ] = '0'
881
+ pos += 2
882
+ case '\n' :
883
+ buf [pos ] = '\\'
884
+ buf [pos + 1 ] = 'n'
885
+ pos += 2
886
+ case '\r' :
887
+ buf [pos ] = '\\'
888
+ buf [pos + 1 ] = 'r'
889
+ pos += 2
890
+ case '\x1a' :
891
+ buf [pos ] = '\\'
892
+ buf [pos + 1 ] = 'Z'
893
+ pos += 2
894
+ case '\'' :
895
+ buf [pos ] = '\\'
896
+ buf [pos + 1 ] = '\''
897
+ pos += 2
898
+ case '"' :
899
+ buf [pos ] = '\\'
900
+ buf [pos + 1 ] = '"'
901
+ pos += 2
902
+ case '\\' :
903
+ buf [pos ] = '\\'
904
+ buf [pos + 1 ] = '\\'
905
+ pos += 2
906
+ default :
907
+ buf [pos ] = c
908
+ pos += 1
909
+ }
910
+ }
911
+
912
+ return buf [:pos ]
913
+ }
914
+
915
+ // escapeBytesQuotes escapes apostrophes in []byte by doubling them up.
865
916
// This escapes the contents of a string by doubling up any apostrophes that
866
917
// it contains. This is used when the NO_BACKSLASH_ESCAPES SQL_MODE is in
867
918
// effect on the server.
868
919
// https://github.com/mysql/mysql-server/blob/mysql-5.7.5/mysys/charset.c#L963-L1038
869
- func escapeQuotes (buf , v []byte ) []byte {
920
+ func escapeBytesQuotes (buf , v []byte ) []byte {
870
921
pos := len (buf )
871
922
end := pos + len (v )* 2
872
923
if cap (buf ) < end {
@@ -889,3 +940,29 @@ func escapeQuotes(buf, v []byte) []byte {
889
940
890
941
return buf [:pos ]
891
942
}
943
+
944
+ // escapeStringQuotes is similar to escapeBytesQuotes but for string.
945
+ func escapeStringQuotes (buf []byte , v string ) []byte {
946
+ pos := len (buf )
947
+ end := pos + len (v )* 2
948
+ if cap (buf ) < end {
949
+ n := make ([]byte , pos + end )
950
+ copy (n , buf )
951
+ buf = n
952
+ }
953
+ buf = buf [0 :end ]
954
+
955
+ for i := 0 ; i < len (v ); i ++ {
956
+ c := v [i ]
957
+ if c == '\'' {
958
+ buf [pos ] = '\''
959
+ buf [pos + 1 ] = '\''
960
+ pos += 2
961
+ } else {
962
+ buf [pos ] = c
963
+ pos ++
964
+ }
965
+ }
966
+
967
+ return buf [:pos ]
968
+ }
0 commit comments