Call scan_once and handle the result. Returns (value, end_char_idx, end_byte_idx).
(
&self,
scan_once: &PyObjectRef,
pystr: PyUtf8StrRef,
char_idx: usize,
byte_idx: usize,
memo: &mut HashMap<String, PyStrRef>,
| 505 | /// Call scan_once and handle the result. |
| 506 | /// Returns (value, end_char_idx, end_byte_idx). |
| 507 | fn call_scan_once( |
| 508 | &self, |
| 509 | scan_once: &PyObjectRef, |
| 510 | pystr: PyUtf8StrRef, |
| 511 | char_idx: usize, |
| 512 | byte_idx: usize, |
| 513 | memo: &mut HashMap<String, PyStrRef>, |
| 514 | vm: &VirtualMachine, |
| 515 | ) -> PyResult<(PyObjectRef, usize, usize)> { |
| 516 | let bytes = pystr.as_bytes(); |
| 517 | let wtf8 = pystr.as_wtf8(); |
| 518 | let s = pystr.as_str(); |
| 519 | |
| 520 | let first_byte = match bytes.get(byte_idx) { |
| 521 | Some(&b) => b, |
| 522 | None => return Err(self.make_decode_error("Expecting value", pystr, char_idx, vm)), |
| 523 | }; |
| 524 | |
| 525 | match first_byte { |
| 526 | b'"' => { |
| 527 | // String - pass slice starting after the quote |
| 528 | let (wtf8_result, chars_consumed, bytes_consumed) = |
| 529 | machinery::scanstring(&wtf8[byte_idx + 1..], char_idx + 1, self.strict) |
| 530 | .map_err(|e| py_decode_error(e, pystr.clone().into_wtf8(), vm))?; |
| 531 | let py_str = vm.ctx.new_str(wtf8_result.to_string()); |
| 532 | Ok(( |
| 533 | py_str.into(), |
| 534 | char_idx + 1 + chars_consumed, |
| 535 | byte_idx + 1 + bytes_consumed, |
| 536 | )) |
| 537 | } |
| 538 | b'{' => { |
| 539 | // Object |
| 540 | self.parse_object(pystr, char_idx + 1, byte_idx + 1, scan_once, memo, vm) |
| 541 | } |
| 542 | b'[' => { |
| 543 | // Array |
| 544 | self.parse_array(pystr, char_idx + 1, byte_idx + 1, scan_once, memo, vm) |
| 545 | } |
| 546 | b'n' if starts_with_bytes(&bytes[byte_idx..], b"null") => { |
| 547 | // null |
| 548 | Ok((vm.ctx.none(), char_idx + 4, byte_idx + 4)) |
| 549 | } |
| 550 | b't' if starts_with_bytes(&bytes[byte_idx..], b"true") => { |
| 551 | // true |
| 552 | Ok((vm.ctx.new_bool(true).into(), char_idx + 4, byte_idx + 4)) |
| 553 | } |
| 554 | b'f' if starts_with_bytes(&bytes[byte_idx..], b"false") => { |
| 555 | // false |
| 556 | Ok((vm.ctx.new_bool(false).into(), char_idx + 5, byte_idx + 5)) |
| 557 | } |
| 558 | b'N' if starts_with_bytes(&bytes[byte_idx..], b"NaN") => { |
| 559 | // NaN |
| 560 | let result = self.parse_constant.call(("NaN",), vm)?; |
| 561 | Ok((result, char_idx + 3, byte_idx + 3)) |
| 562 | } |
| 563 | b'I' if starts_with_bytes(&bytes[byte_idx..], b"Infinity") => { |
| 564 | // Infinity |
no test coverage detected