(data string, lines bool, limit int)
| 157 | } |
| 158 | |
| 159 | func newBufferWithLimit(data string, lines bool, limit int) (Buffer, []int32, error) { |
| 160 | if len(data) == 0 { |
| 161 | return nilBuffer, []int32{0}, nil |
| 162 | } |
| 163 | if limit >= 0 && len(data) > limit { |
| 164 | size := countRemainingCodePoints(data, 0, 0) |
| 165 | if size > limit { |
| 166 | return nil, nil, &SizeLimitError{ |
| 167 | Size: size, |
| 168 | Limit: limit, |
| 169 | } |
| 170 | } |
| 171 | } |
| 172 | |
| 173 | // The resulting buffers store one element per code point, so the worst case |
| 174 | // element count never exceeds len(data). |
| 175 | var ( |
| 176 | idx = 0 |
| 177 | off int32 = 0 |
| 178 | buf8 = make([]byte, 0, len(data)) |
| 179 | buf16 []uint16 |
| 180 | buf32 []rune |
| 181 | offs []int32 |
| 182 | ) |
| 183 | for idx < len(data) { |
| 184 | r, s := utf8.DecodeRuneInString(data[idx:]) |
| 185 | idx += s |
| 186 | if lines && r == '\n' { |
| 187 | offs = append(offs, off+1) |
| 188 | } |
| 189 | if r < utf8.RuneSelf { |
| 190 | buf8 = append(buf8, byte(r)) |
| 191 | off++ |
| 192 | continue |
| 193 | } |
| 194 | if r <= 0xffff { |
| 195 | buf16 = make([]uint16, len(buf8), len(data)) |
| 196 | for i, v := range buf8 { |
| 197 | buf16[i] = uint16(v) |
| 198 | } |
| 199 | buf8 = nil |
| 200 | buf16 = append(buf16, uint16(r)) |
| 201 | off++ |
| 202 | goto copy16 |
| 203 | } |
| 204 | buf32 = make([]rune, len(buf8), len(data)) |
| 205 | for i, v := range buf8 { |
| 206 | buf32[i] = rune(uint32(v)) |
| 207 | } |
| 208 | buf8 = nil |
| 209 | buf32 = append(buf32, r) |
| 210 | off++ |
| 211 | goto copy32 |
| 212 | } |
| 213 | if lines { |
| 214 | offs = append(offs, off+1) |
| 215 | } |
| 216 | return &asciiBuffer{ |
no test coverage detected