1use std::path::PathBuf;
207use std::ffi::CString;
208
209#[macro_use]
210mod parse_memory_data;
211mod big_endian;
212mod little_endian;
213
214#[derive(Debug, Clone, PartialEq, PartialOrd, Hash, Eq, Ord)]
215pub enum ParseError {
216 WrongInputSize { expected_len: usize, got: Vec<u8> },
217 UnableToParseBool(BoolParseError),
218 NoEndiannessGiven([u8;2]),
219 InvalidPixelType(u8),
220 FromBytesWithNulError(Vec<u8>),
221 PathContainsNonUTF8Chars(CString),
222}
223
224#[derive(Debug, Copy, Clone, PartialEq, PartialOrd, Hash, Eq, Ord)]
225pub struct BoolParseError([u8;2], u8);
226
227impl From<BoolParseError> for ParseError {
228 fn from(e: BoolParseError) -> Self {
229 ParseError::UnableToParseBool(e)
230 }
231}
232
233#[derive(Debug, Clone, PartialEq, PartialOrd)]
235pub struct Raster {
236 pub endian: Endian,
238 pub version: u16,
240 pub scale_x: f64,
242 pub scale_y: f64,
244 pub ip_x: f64,
246 pub ip_y: f64,
248 pub skew_x: f64,
250 pub skew_y: f64,
252 pub srid: i32,
254 pub width: u16,
256 pub height: u16,
258 pub bands: Vec<RasterBand>,
260}
261
262#[inline]
263fn take_slice_1_byte(input: &[u8]) -> Result<([u8;2], &[u8]), ParseError> {
264 use self::ParseError::*;
265 const MIN_LEN: usize = 2;
266 if input.len() < MIN_LEN {
267 return Err(WrongInputSize { expected_len: MIN_LEN, got: input.to_vec() });
268 }
269 unsafe {
270 let a = input.get_unchecked(0);
271 let b = input.get_unchecked(1);
272 Ok(([*a, *b], &input[MIN_LEN..]))
273 }
274}
275
276#[inline]
277fn take_slice_2_bytes(input: &[u8]) -> Result<([u8;4], &[u8]), ParseError> {
278 use self::ParseError::*;
279 const MIN_LEN: usize = 4;
280 if input.len() < MIN_LEN {
281 return Err(WrongInputSize { expected_len: MIN_LEN, got: input.to_vec() });
282 }
283 unsafe {
284 let a = input.get_unchecked(0);
285 let b = input.get_unchecked(1);
286 let c = input.get_unchecked(2);
287 let d = input.get_unchecked(3);
288 Ok(([*a, *b, *c, *d], &input[MIN_LEN..]))
289 }
290}
291
292#[inline]
293fn take_slice_4_bytes(input: &[u8]) -> Result<([u8;8], &[u8]), ParseError> {
294 use self::ParseError::*;
295 const MIN_LEN: usize = 8;
296 if input.len() < MIN_LEN {
297 return Err(WrongInputSize { expected_len: MIN_LEN, got: input.to_vec() });
298 }
299 unsafe {
300 let a = input.get_unchecked(0);
301 let b = input.get_unchecked(1);
302 let c = input.get_unchecked(2);
303 let d = input.get_unchecked(3);
304 let e = input.get_unchecked(4);
305 let f = input.get_unchecked(5);
306 let g = input.get_unchecked(6);
307 let h = input.get_unchecked(7);
308 Ok(([*a, *b, *c, *d, *e, *f, *g, *h], &input[MIN_LEN..]))
309 }
310}
311
312#[inline]
313fn take_slice_8_bytes(input: &[u8]) -> Result<([u8;16], &[u8]), ParseError> {
314 use self::ParseError::*;
315 const MIN_LEN: usize = 16;
316 if input.len() < MIN_LEN {
317 return Err(WrongInputSize { expected_len: MIN_LEN, got: input.to_vec() });
318 }
319 unsafe {
320 let a = input.get_unchecked(0);
321 let b = input.get_unchecked(1);
322 let c = input.get_unchecked(2);
323 let d = input.get_unchecked(3);
324 let e = input.get_unchecked(4);
325 let f = input.get_unchecked(5);
326 let g = input.get_unchecked(6);
327 let h = input.get_unchecked(7);
328
329 let i = input.get_unchecked(8);
330 let j = input.get_unchecked(9);
331 let k = input.get_unchecked(10);
332 let l = input.get_unchecked(11);
333 let m = input.get_unchecked(12);
334 let n = input.get_unchecked(13);
335 let o = input.get_unchecked(14);
336 let p = input.get_unchecked(15);
337
338 Ok((
339 [*a, *b, *c, *d, *e, *f, *g, *h,
340 *i, *j, *k, *l, *m, *n, *o, *p],
341 &input[MIN_LEN..]
342 ))
343 }
344}
345
346impl Raster {
347
348 pub fn to_wkb_string(self) -> String {
350 match self.endian {
351 Endian::Big => self.to_wkb_string_big_endian(),
352 Endian::Little => self.to_wkb_string_little_endian(),
353 }
354 }
355
356 pub fn from_wkb_string(string_bytes: &[u8]) -> Result<Self, ParseError> {
357 use self::ParseError::*;
358 match take_slice_1_byte(string_bytes)? {
359 ([b'0', b'0'], input) => Self::from_wkb_string_big_endian(input),
360 ([b'0', b'1'], input) => Self::from_wkb_string_little_endian(input),
361 (other, _) => Err(NoEndiannessGiven(other)),
362 }
363 }
364
365 fn from_wkb_string_big_endian(input: &[u8]) -> Result<Self, ParseError> {
366
367 use crate::big_endian::*;
368
369 let (version_bytes, input) = take_slice_2_bytes(input)?;
370 let version = parse_u16_be(version_bytes);
371
372 let (nbands_bytes, input) = take_slice_2_bytes(input)?;
373 let nbands = parse_u16_be(nbands_bytes);
374
375 let (scale_x_bytes, input) = take_slice_8_bytes(input)?;
376 let scale_x = parse_f64_be(scale_x_bytes);
377
378 let (scale_y_bytes, input) = take_slice_8_bytes(input)?;
379 let scale_y = parse_f64_be(scale_y_bytes);
380
381 let (ip_x_bytes, input) = take_slice_8_bytes(input)?;
382 let ip_x = parse_f64_be(ip_x_bytes);
383
384 let (ip_y_bytes, input) = take_slice_8_bytes(input)?;
385 let ip_y = parse_f64_be(ip_y_bytes);
386
387 let (skew_x_bytes, input) = take_slice_8_bytes(input)?;
388 let skew_x = parse_f64_be(skew_x_bytes);
389
390 let (skew_y_bytes, input) = take_slice_8_bytes(input)?;
391 let skew_y = parse_f64_be(skew_y_bytes);
392
393 let (srid_bytes, input) = take_slice_4_bytes(input)?;
394 let srid = parse_i32_be(srid_bytes);
395
396 let (width_bytes, input) = take_slice_2_bytes(input)?;
397 let width = parse_u16_be(width_bytes);
398
399 let (height_bytes, mut input) = take_slice_2_bytes(input)?;
400 let height = parse_u16_be(height_bytes);
401
402 let mut raster_bands = Vec::with_capacity(nbands as usize);
403
404 for _ in 0..(nbands as usize) {
405 let (raster_band, rt_input) = RasterBand::from_wkb_string_big_endian(input, width, height)?;
406 input = rt_input;
407 raster_bands.push(raster_band);
408 }
409
410 Ok(Raster {
411 endian: Endian::Big,
412 version,
413 scale_x,
414 scale_y,
415 ip_x,
416 ip_y,
417 skew_x,
418 skew_y,
419 srid,
420 width,
421 height,
422 bands: raster_bands,
423 })
424 }
425
426 fn from_wkb_string_little_endian(input: &[u8]) -> Result<Self, ParseError> {
427 use crate::little_endian::*;
428
429 let (version_bytes, input) = take_slice_2_bytes(input)?;
430 let version = parse_u16_le(version_bytes);
431
432 let (nbands_bytes, input) = take_slice_2_bytes(input)?;
433 let nbands = parse_u16_le(nbands_bytes);
434
435 let (scale_x_bytes, input) = take_slice_8_bytes(input)?;
436 let scale_x = parse_f64_le(scale_x_bytes);
437
438 let (scale_y_bytes, input) = take_slice_8_bytes(input)?;
439 let scale_y = parse_f64_le(scale_y_bytes);
440
441 let (ip_x_bytes, input) = take_slice_8_bytes(input)?;
442 let ip_x = parse_f64_le(ip_x_bytes);
443
444 let (ip_y_bytes, input) = take_slice_8_bytes(input)?;
445 let ip_y = parse_f64_le(ip_y_bytes);
446
447 let (skew_x_bytes, input) = take_slice_8_bytes(input)?;
448 let skew_x = parse_f64_le(skew_x_bytes);
449
450 let (skew_y_bytes, input) = take_slice_8_bytes(input)?;
451 let skew_y = parse_f64_le(skew_y_bytes);
452
453 let (srid_bytes, input) = take_slice_4_bytes(input)?;
454 let srid = parse_i32_le(srid_bytes);
455
456 let (width_bytes, input) = take_slice_2_bytes(input)?;
457 let width = parse_u16_le(width_bytes);
458
459 let (height_bytes, mut input) = take_slice_2_bytes(input)?;
460 let height = parse_u16_le(height_bytes);
461
462 let mut raster_bands = Vec::with_capacity(nbands as usize);
463
464 for _ in 0..(nbands as usize) {
465 let (raster_band, rt_input) = RasterBand::from_wkb_string_little_endian(input, width, height)?;
466 input = rt_input;
467 raster_bands.push(raster_band);
468 }
469
470 Ok(Raster {
471 endian: Endian::Little,
472 version,
473 scale_x,
474 scale_y,
475 ip_x,
476 ip_y,
477 skew_x,
478 skew_y,
479 srid,
480 width,
481 height,
482 bands: raster_bands,
483 })
484 }
485
486 fn to_wkb_string_big_endian(self) -> String {
487
488 use crate::big_endian::*;
489
490 let mut string_bytes = Vec::new();
491
492 write_u8_be(&mut string_bytes, self.endian as u8);
494 write_u16_be(&mut string_bytes, self.version);
496 write_u16_be(&mut string_bytes, self.bands.len() as u16);
498 write_f64_be(&mut string_bytes, self.scale_x);
500 write_f64_be(&mut string_bytes, self.scale_y);
501 write_f64_be(&mut string_bytes, self.ip_x);
502 write_f64_be(&mut string_bytes, self.ip_y);
503 write_f64_be(&mut string_bytes, self.skew_x);
504 write_f64_be(&mut string_bytes, self.skew_y);
505
506 write_i32_be(&mut string_bytes, self.srid);
508 write_u16_be(&mut string_bytes, self.width);
510 write_u16_be(&mut string_bytes, self.height);
512
513 for band in self.bands {
514
515 let config = 0 |
517 (band.data.is_offline() as u8) << 7 |
518 (band.data.get_pixtype().has_nodata_value() as u8) << 6 |
519 (band.is_nodata_value as u8) << 5 |
520 (0_u8 << 4) |
521 band.data.get_pixtype().get_type() & 0b00001111;
522
523 write_u8_be(&mut string_bytes, config);
524
525 string_bytes.append(&mut band.data.get_pixtype().get_nodata_value_as_string_big_endian());
527
528 string_bytes.append(&mut band.data.to_wkb_string_big_endian());
530 }
531
532 unsafe { String::from_utf8_unchecked(string_bytes) }
533 }
534
535 fn to_wkb_string_little_endian(self) -> String {
536
537 use self::little_endian::*;
538
539 let mut string_bytes = Vec::new();
540
541 write_u8_le(&mut string_bytes, self.endian as u8);
543 write_u16_le(&mut string_bytes, self.version);
545 write_u16_le(&mut string_bytes, self.bands.len() as u16);
547 write_f64_le(&mut string_bytes, self.scale_x);
549 write_f64_le(&mut string_bytes, self.scale_y);
550 write_f64_le(&mut string_bytes, self.ip_x);
551 write_f64_le(&mut string_bytes, self.ip_y);
552 write_f64_le(&mut string_bytes, self.skew_x);
553 write_f64_le(&mut string_bytes, self.skew_y);
554
555 write_i32_le(&mut string_bytes, self.srid);
557 write_u16_le(&mut string_bytes, self.width);
559 write_u16_le(&mut string_bytes, self.height);
561
562 for band in self.bands {
563
564 let config = 0 |
569 (band.data.is_offline() as u8) << 7 |
570 (band.data.get_pixtype().has_nodata_value() as u8) << 6 |
571 (band.is_nodata_value as u8) << 5 |
572 (0_u8 << 4) |
573 band.data.get_pixtype().get_type() & 0b00001111;
574
575 write_u8_le(&mut string_bytes, config);
576
577 string_bytes.append(&mut band.data.get_pixtype().get_nodata_value_as_string_little_endian());
579
580 string_bytes.append(&mut band.data.to_wkb_string_little_endian());
582 }
583
584 unsafe { String::from_utf8_unchecked(string_bytes) }
585 }
586}
587
588#[derive(Debug, Copy, Clone, PartialEq, Eq, PartialOrd, Ord, Hash)]
590#[repr(u8)]
591pub enum Endian {
592 Big = 0,
593 Little = 1,
594}
595
596#[derive(Debug, Clone, PartialEq, PartialOrd)]
598pub struct RasterBand {
599 pub is_nodata_value: bool,
602 pub data: RasterDataSource,
604}
605
606impl RasterBand {
607
608 fn from_wkb_string_big_endian(input: &[u8], width: u16, height: u16) -> Result<(Self, &[u8]), ParseError> {
609 use crate::big_endian::*;
610 use self::ParseError::*;
611
612
613 let (pixinfo_bytes, mut input) = take_slice_1_byte(input)?;
614 let pixinfo = parse_u8_be(pixinfo_bytes);
615 let is_offline = ((pixinfo & 0b10000000) >> 7) != 0;
616 let has_nodata_value = ((pixinfo & 0b01000000) >> 6) != 0;
617 let is_nodata_value = ((pixinfo & 0b00100000) >> 5) != 0; let pixtype = pixinfo & 0b00001111;
619
620
621 let pixtype = match pixtype {
622 0 => {
623 let nodata = if has_nodata_value {
624 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
625 input = pt_input;
626 Some(parse_bool_be(nodata_bytes)?)
627 } else {
628 let (_, pt_input) = take_slice_1_byte(input)?;
629 input = pt_input;
630 None
631 };
632 PixType::Bool1Bit(nodata)
633 },
634 1 => {
635 let nodata = if has_nodata_value {
636 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
637 input = pt_input;
638 Some(parse_u8_be(nodata_bytes))
639 } else {
640 let (_, pt_input) = take_slice_1_byte(input)?;
641 input = pt_input;
642 None
643 };
644 PixType::UInt2(nodata)
645 },
646 2 => {
647 let nodata = if has_nodata_value {
648 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
649 input = pt_input;
650 Some(parse_u8_be(nodata_bytes))
651 } else {
652 let (_, pt_input) = take_slice_1_byte(input)?;
653 input = pt_input;
654 None
655 };
656 PixType::UInt4(nodata)
657 },
658 3 => {
659 let nodata = if has_nodata_value {
660 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
661 input = pt_input;
662 Some(parse_i8_be(nodata_bytes))
663 } else {
664 let (_, pt_input) = take_slice_1_byte(input)?;
665 input = pt_input;
666 None
667 };
668 PixType::Int8(nodata)
669 },
670 4 => {
671 let nodata = if has_nodata_value {
672 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
673 input = pt_input;
674 Some(parse_u8_be(nodata_bytes))
675 } else {
676 let (_, pt_input) = take_slice_1_byte(input)?;
677 input = pt_input;
678 None
679 };
680 PixType::UInt8(nodata)
681 },
682 5 => {
683 let nodata = if has_nodata_value {
684 let (nodata_bytes, pt_input) = take_slice_2_bytes(input)?;
685 input = pt_input;
686 Some(parse_i16_be(nodata_bytes))
687 } else {
688 let (_, pt_input) = take_slice_1_byte(input)?;
689 input = pt_input;
690 None
691 };
692 PixType::Int16(nodata)
693 },
694 6 => {
695 let nodata = if has_nodata_value {
696 let (nodata_bytes, pt_input) = take_slice_2_bytes(input)?;
697 input = pt_input;
698 Some(parse_u16_be(nodata_bytes))
699 } else {
700 let (_, pt_input) = take_slice_1_byte(input)?;
701 input = pt_input;
702 None
703 };
704 PixType::UInt16(nodata)
705 },
706 7 => {
707 let nodata = if has_nodata_value {
708 let (nodata_bytes, pt_input) = take_slice_4_bytes(input)?;
709 input = pt_input;
710 Some(parse_i32_be(nodata_bytes))
711 } else {
712 let (_, pt_input) = take_slice_1_byte(input)?;
713 input = pt_input;
714 None
715 };
716 PixType::Int32(nodata)
717 },
718 8 => {
719 let nodata = if has_nodata_value {
720 let (nodata_bytes, pt_input) = take_slice_4_bytes(input)?;
721 input = pt_input;
722 Some(parse_u32_be(nodata_bytes))
723 } else {
724 let (_, pt_input) = take_slice_1_byte(input)?;
725 input = pt_input;
726 None
727 };
728 PixType::UInt32(nodata)
729 },
730 10 => {
731 let nodata = if has_nodata_value {
732 let (nodata_bytes, pt_input) = take_slice_4_bytes(input)?;
733 input = pt_input;
734 Some(parse_f32_be(nodata_bytes))
735 } else {
736 let (_, pt_input) = take_slice_1_byte(input)?;
737 input = pt_input;
738 None
739 };
740 PixType::Float32(nodata)
741 },
742 11 => {
743 let nodata = if has_nodata_value {
744 let (nodata_bytes, pt_input) = take_slice_8_bytes(input)?;
745 input = pt_input;
746 Some(parse_f64_be(nodata_bytes))
747 } else {
748 let (_, pt_input) = take_slice_1_byte(input)?;
749 input = pt_input;
750 None
751 };
752 PixType::Float64(nodata)
753 },
754 other => return Err(InvalidPixelType(other)),
755 };
756
757
758 let (raster_data_source, input) = if is_offline {
759 RasterDataSource::parse_offline_big_endian(input, pixtype)?
760 } else {
761 RasterDataSource::parse_memory_big_endian(input, pixtype, width, height)?
762 };
763
764
765 Ok((RasterBand {
766 is_nodata_value,
767 data: raster_data_source,
768 }, input))
769 }
770
771 fn from_wkb_string_little_endian(input: &[u8], width: u16, height: u16) -> Result<(Self, &[u8]), ParseError> {
772 use crate::little_endian::*;
773 use self::ParseError::*;
774
775
776 let (pixinfo_bytes, mut input) = take_slice_1_byte(input)?;
777 let pixinfo = parse_u8_le(pixinfo_bytes);
778 let is_offline = ((pixinfo & 0b10000000) >> 7) != 0;
779 let has_nodata_value = ((pixinfo & 0b01000000) >> 6) != 0;
780 let is_nodata_value = ((pixinfo & 0b00100000) >> 5) != 0; let pixtype = pixinfo & 0b00001111;
782
783
784 let pixtype = match pixtype {
785 0 => {
786 let nodata = if has_nodata_value {
787 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
788 input = pt_input;
789 Some(parse_bool_le(nodata_bytes)?)
790 } else {
791 let (_, pt_input) = take_slice_1_byte(input)?;
792 input = pt_input;
793 None
794 };
795 PixType::Bool1Bit(nodata)
796 },
797 1 => {
798 let nodata = if has_nodata_value {
799 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
800 input = pt_input;
801 Some(parse_u8_le(nodata_bytes))
802 } else {
803 let (_, pt_input) = take_slice_1_byte(input)?;
804 input = pt_input;
805 None
806 };
807 PixType::UInt2(nodata)
808 },
809 2 => {
810 let nodata = if has_nodata_value {
811 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
812 input = pt_input;
813 Some(parse_u8_le(nodata_bytes))
814 } else {
815 let (_, pt_input) = take_slice_1_byte(input)?;
816 input = pt_input;
817 None
818 };
819 PixType::UInt4(nodata)
820 },
821 3 => {
822 let nodata = if has_nodata_value {
823 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
824 input = pt_input;
825 Some(parse_i8_le(nodata_bytes))
826 } else {
827 let (_, pt_input) = take_slice_1_byte(input)?;
828 input = pt_input;
829 None
830 };
831 PixType::Int8(nodata)
832 },
833 4 => {
834 let nodata = if has_nodata_value {
835 let (nodata_bytes, pt_input) = take_slice_1_byte(input)?;
836 input = pt_input;
837 Some(parse_u8_le(nodata_bytes))
838 } else {
839 let (_, pt_input) = take_slice_1_byte(input)?;
840 input = pt_input;
841 None
842 };
843 PixType::UInt8(nodata)
844 },
845 5 => {
846 let nodata = if has_nodata_value {
847 let (nodata_bytes, pt_input) = take_slice_2_bytes(input)?;
848 input = pt_input;
849 Some(parse_i16_le(nodata_bytes))
850 } else {
851 let (_, pt_input) = take_slice_1_byte(input)?;
852 input = pt_input;
853 None
854 };
855 PixType::Int16(nodata)
856 },
857 6 => {
858 let nodata = if has_nodata_value {
859 let (nodata_bytes, pt_input) = take_slice_2_bytes(input)?;
860 input = pt_input;
861 Some(parse_u16_le(nodata_bytes))
862 } else {
863 let (_, pt_input) = take_slice_1_byte(input)?;
864 input = pt_input;
865 None
866 };
867 PixType::UInt16(nodata)
868 },
869 7 => {
870 let nodata = if has_nodata_value {
871 let (nodata_bytes, pt_input) = take_slice_4_bytes(input)?;
872 input = pt_input;
873 Some(parse_i32_le(nodata_bytes))
874 } else {
875 let (_, pt_input) = take_slice_1_byte(input)?;
876 input = pt_input;
877 None
878 };
879 PixType::Int32(nodata)
880 },
881 8 => {
882 let nodata = if has_nodata_value {
883 let (nodata_bytes, pt_input) = take_slice_4_bytes(input)?;
884 input = pt_input;
885 Some(parse_u32_le(nodata_bytes))
886 } else {
887 let (_, pt_input) = take_slice_1_byte(input)?;
888 input = pt_input;
889 None
890 };
891 PixType::UInt32(nodata)
892 },
893 10 => {
894 let nodata = if has_nodata_value {
895 let (nodata_bytes, pt_input) = take_slice_4_bytes(input)?;
896 input = pt_input;
897 Some(parse_f32_le(nodata_bytes))
898 } else {
899 let (_, pt_input) = take_slice_1_byte(input)?;
900 input = pt_input;
901 None
902 };
903 PixType::Float32(nodata)
904 },
905 11 => {
906 let nodata = if has_nodata_value {
907 let (nodata_bytes, pt_input) = take_slice_8_bytes(input)?;
908 input = pt_input;
909 Some(parse_f64_le(nodata_bytes))
910 } else {
911 let (_, pt_input) = take_slice_1_byte(input)?;
912 input = pt_input;
913 None
914 };
915 PixType::Float64(nodata)
916 },
917 other => return Err(InvalidPixelType(other)),
918 };
919
920 let (raster_data_source, input) = if is_offline {
921 RasterDataSource::parse_offline_little_endian(input, pixtype)?
922 } else {
923 RasterDataSource::parse_memory_little_endian(input, pixtype, width, height)?
924 };
925
926
927 Ok((RasterBand {
928 is_nodata_value,
929 data: raster_data_source,
930 }, input))
931 }
932}
933
934impl RasterDataSource {
935
936 pub fn is_offline(&self) -> bool {
938 use self::RasterDataSource::*;
939 match self {
940 Offline(_) => true,
941 InMemory(_) => false,
942 }
943 }
944
945 pub fn get_pixtype(&self) -> PixType {
946 use self::RasterDataSource::*;
947 match &self {
948 Offline(o) => o.pixtype,
949 InMemory(i) => i.get_pixtype(),
950 }
951 }
952
953 fn parse_offline_big_endian(input: &[u8], pixtype: PixType) -> Result<(Self, &[u8]), ParseError> {
954 use crate::big_endian::*;
955 use std::ffi::CStr;
956
957 let (band_bytes, mut input) = take_slice_1_byte(input)?;
958 let band = parse_i8_be(band_bytes);
959
960 let mut path_bytes = Vec::new();
961 loop {
962
963 let (byte, new_input) = take_slice_1_byte(input)?;
964 input = new_input;
965 let parsed = parse_u8_be(byte);
966 path_bytes.push(parsed);
967
968 if parsed == b'\0' {
969 break;
970 }
971 }
972
973 let path = CStr::from_bytes_with_nul(&path_bytes)
974 .map_err(|_| ParseError::FromBytesWithNulError(path_bytes.clone()))?;
975 let path = CString::from(path);
976 let path = PathBuf::from(path.clone().into_string()
977 .map_err(|_| ParseError::PathContainsNonUTF8Chars(path.to_owned()))?);
978
979 Ok((RasterDataSource::Offline(OfflineRasterData {
980 band,
981 path,
982 pixtype,
983 }), input))
984
985 }
986
987 fn parse_offline_little_endian(input: &[u8], pixtype: PixType) -> Result<(Self, &[u8]), ParseError> {
988
989 use crate::little_endian::*;
990 use std::ffi::CStr;
991
992 let (band_bytes, mut input) = take_slice_1_byte(input)?;
993 let band = parse_i8_le(band_bytes);
994
995 let mut path_bytes = Vec::new();
996 loop {
997
998 let (byte, new_input) = take_slice_1_byte(input)?;
999 input = new_input;
1000 let parsed = parse_u8_le(byte);
1001 path_bytes.push(parsed);
1002
1003 if parsed == b'\0' {
1004 break;
1005 }
1006 }
1007
1008 let path = CStr::from_bytes_with_nul(&path_bytes)
1009 .map_err(|_| ParseError::FromBytesWithNulError(path_bytes.clone()))?;
1010 let path = CString::from(path);
1011 let path = PathBuf::from(path.clone().into_string()
1012 .map_err(|_| ParseError::PathContainsNonUTF8Chars(path.to_owned()))?);
1013
1014 Ok((RasterDataSource::Offline(OfflineRasterData {
1015 band,
1016 path,
1017 pixtype,
1018 }), input))
1019 }
1020
1021 fn parse_memory_big_endian(input: &[u8], pixtype: PixType, width: u16, height: u16) -> Result<(Self, &[u8]), ParseError> {
1022
1023
1024 parse_memory_data_fns!(
1025 crate::big_endian,
1026
1027 parse_memory_data_bool_be,
1028 parse_memory_data_uint2_be,
1029 parse_memory_data_uint4_be,
1030 parse_memory_data_int8_be,
1031 parse_memory_data_uint8_be,
1032 parse_memory_data_int16_be,
1033 parse_memory_data_uint16_be,
1034 parse_memory_data_int32_be,
1035 parse_memory_data_uint32_be,
1036 parse_memory_data_f32_be,
1037 parse_memory_data_f64_be,
1038
1039 parse_bool_be,
1040 parse_uint2_be,
1041 parse_uint4_be,
1042 parse_i8_be,
1043 parse_u8_be,
1044 parse_i16_be,
1045 parse_u16_be,
1046 parse_i32_be,
1047 parse_u32_be,
1048 parse_f32_be,
1049 parse_f64_be,
1050 );
1051
1052 let ret = gen_parse_function_body!(
1053 parse_memory_data_bool_be,
1054 parse_memory_data_uint2_be,
1055 parse_memory_data_uint4_be,
1056 parse_memory_data_int8_be,
1057 parse_memory_data_uint8_be,
1058 parse_memory_data_int16_be,
1059 parse_memory_data_uint16_be,
1060 parse_memory_data_int32_be,
1061 parse_memory_data_uint32_be,
1062 parse_memory_data_f32_be,
1063 parse_memory_data_f64_be,
1064
1065 input,
1066 pixtype,
1067 width,
1068 height,
1069 );
1070
1071 ret
1072 }
1073
1074 fn parse_memory_little_endian(input: &[u8], pixtype: PixType, width: u16, height: u16) -> Result<(Self, &[u8]), ParseError> {
1075
1076
1077 parse_memory_data_fns!(
1078 crate::little_endian,
1079
1080 parse_memory_data_bool_le,
1081 parse_memory_data_uint2_le,
1082 parse_memory_data_uint4_le,
1083 parse_memory_data_int8_le,
1084 parse_memory_data_uint8_le,
1085 parse_memory_data_int16_le,
1086 parse_memory_data_uint16_le,
1087 parse_memory_data_int32_le,
1088 parse_memory_data_uint32_le,
1089 parse_memory_data_f32_le,
1090 parse_memory_data_f64_le,
1091
1092 parse_bool_le,
1093 parse_uint2_le,
1094 parse_uint4_le,
1095 parse_i8_le,
1096 parse_u8_le,
1097 parse_i16_le,
1098 parse_u16_le,
1099 parse_i32_le,
1100 parse_u32_le,
1101 parse_f32_le,
1102 parse_f64_le,
1103 );
1104
1105 let ret = gen_parse_function_body!(
1106 parse_memory_data_bool_le,
1107 parse_memory_data_uint2_le,
1108 parse_memory_data_uint4_le,
1109 parse_memory_data_int8_le,
1110 parse_memory_data_uint8_le,
1111 parse_memory_data_int16_le,
1112 parse_memory_data_uint16_le,
1113 parse_memory_data_int32_le,
1114 parse_memory_data_uint32_le,
1115 parse_memory_data_f32_le,
1116 parse_memory_data_f64_le,
1117
1118 input,
1119 pixtype,
1120 width,
1121 height,
1122 );
1123
1124 ret
1125 }
1126}
1127
1128#[derive(Debug, Copy, Clone, PartialEq, PartialOrd)]
1130#[repr(u16)]
1131pub enum PixType {
1132 Bool1Bit(Option<bool>),
1133 UInt2(Option<u8>),
1134 UInt4(Option<u8>),
1135 Int8(Option<i8>),
1136 UInt8(Option<u8>),
1137 Int16(Option<i16>),
1138 UInt16(Option<u16>),
1139 Int32(Option<i32>),
1140 UInt32(Option<u32>),
1141 Float32(Option<f32>),
1142 Float64(Option<f64>),
1143}
1144
1145impl PixType {
1146 fn get_type(&self) -> u8 {
1147 use self::PixType::*;
1148 match self {
1149 Bool1Bit(_) => 0,
1150 UInt2(_) => 1,
1151 UInt4(_) => 2,
1152 Int8(_) => 3,
1153 UInt8(_) => 4,
1154 Int16(_) => 5,
1155 UInt16(_) => 6,
1156 Int32(_) => 7,
1157 UInt32(_) => 8, Float32(_) => 10,
1159 Float64(_) => 11,
1160 }
1161 }
1162
1163 pub fn has_nodata_value(&self) -> bool {
1164 use self::PixType::*;
1165 match self {
1166 | Bool1Bit(Some(_))
1167 | UInt2(Some(_))
1168 | UInt4(Some(_))
1169 | Int8(Some(_))
1170 | UInt8(Some(_))
1171 | Int16(Some(_))
1172 | UInt16(Some(_))
1173 | Int32(Some(_))
1174 | UInt32(Some(_))
1175 | Float32(Some(_))
1176 | Float64(Some(_)) => true,
1177 _ => false,
1178 }
1179 }
1180
1181 #[inline]
1182 fn get_nodata_value_as_string_big_endian(&self) -> Vec<u8> {
1183
1184 use crate::big_endian::*;
1185 use self::PixType::*;
1186
1187 let mut s = Vec::new();
1188
1189 match self {
1190 Bool1Bit(Some(b)) => { write_bool_be(&mut s, *b); },
1191 UInt2(Some(b)) => { write_u8_be(&mut s, *b); },
1192 UInt4(Some(b)) => { write_u8_be(&mut s, *b); },
1193 Int8(Some(b)) => { write_i8_be(&mut s, *b); },
1194 UInt8(Some(b)) => { write_u8_be(&mut s, *b); }
1195 Int16(Some(b)) => { write_i16_be(&mut s, *b); }
1196 UInt16(Some(b)) => { write_u16_be(&mut s, *b); }
1197 Int32(Some(b)) => { write_i32_be(&mut s, *b); }
1198 UInt32(Some(b)) => { write_u32_be(&mut s, *b); }
1199 Float32(Some(b)) => { write_f32_be(&mut s, *b); }
1200 Float64(Some(b)) => { write_f64_be(&mut s, *b); }
1201 _ => { write_u8_be(&mut s, 0); },
1202 }
1203
1204 s
1205 }
1206
1207 #[inline]
1208 fn get_nodata_value_as_string_little_endian(&self) -> Vec<u8> {
1209
1210 use self::little_endian::*;
1211 use self::PixType::*;
1212
1213 let mut s = Vec::new();
1214
1215 match self {
1216 Bool1Bit(Some(b)) => { write_bool_le(&mut s, *b); },
1217 UInt2(Some(b)) => { write_u8_le(&mut s, *b); },
1218 UInt4(Some(b)) => { write_u8_le(&mut s, *b); },
1219 Int8(Some(b)) => { write_i8_le(&mut s, *b); },
1220 UInt8(Some(b)) => { write_u8_le(&mut s, *b); }
1221 Int16(Some(b)) => { write_i16_le(&mut s, *b); }
1222 UInt16(Some(b)) => { write_u16_le(&mut s, *b); }
1223 Int32(Some(b)) => { write_i32_le(&mut s, *b); }
1224 UInt32(Some(b)) => { write_u32_le(&mut s, *b); }
1225 Float32(Some(b)) => { write_f32_le(&mut s, *b); }
1226 Float64(Some(b)) => { write_f64_le(&mut s, *b); }
1227 _ => { write_u8_le(&mut s, 0); },
1228 }
1229
1230 s
1231 }
1232}
1233
1234#[derive(Debug, Clone, PartialEq, PartialOrd)]
1236pub enum RasterDataSource {
1237 Offline(OfflineRasterData),
1239 InMemory(InMemoryRasterData),
1243}
1244
1245#[derive(Debug, Clone, PartialEq, PartialOrd)]
1247pub struct OfflineRasterData {
1248 pub band: i8,
1250 pub path: PathBuf,
1252 pub pixtype: PixType,
1254}
1255
1256#[derive(Debug, Clone, PartialEq, PartialOrd)]
1258pub enum InMemoryRasterData {
1259 Bool1Bit { data: Vec<Vec<bool>>, nodata: Option<bool> },
1260 UInt2 { data: Vec<Vec<u8>>, nodata: Option<u8> },
1261 UInt4 { data: Vec<Vec<u8>>, nodata: Option<u8> },
1262 Int8 { data: Vec<Vec<i8>>, nodata: Option<i8> },
1263 UInt8 { data: Vec<Vec<u8>>, nodata: Option<u8> },
1264 Int16 { data: Vec<Vec<i16>>, nodata: Option<i16> },
1265 UInt16 { data: Vec<Vec<u16>>, nodata: Option<u16> },
1266 Int32 { data: Vec<Vec<i32>>, nodata: Option<i32> },
1267 UInt32 { data: Vec<Vec<u32>>, nodata: Option<u32> },
1268 Float32 { data: Vec<Vec<f32>>, nodata: Option<f32> },
1269 Float64 { data: Vec<Vec<f64>>, nodata: Option<f64> },
1270}
1271
1272impl InMemoryRasterData {
1273 pub fn get_pixtype(&self) -> PixType {
1275 match &self {
1276 InMemoryRasterData::Bool1Bit { nodata, .. } => PixType::Bool1Bit(*nodata),
1277 InMemoryRasterData::UInt2 { nodata, .. } => PixType::UInt2(*nodata),
1278 InMemoryRasterData::UInt4 { nodata, .. } => PixType::UInt4(*nodata),
1279 InMemoryRasterData::Int8 { nodata, .. } => PixType::Int8(*nodata),
1280 InMemoryRasterData::UInt8 { nodata, .. } => PixType::UInt8(*nodata),
1281 InMemoryRasterData::Int16 { nodata, .. } => PixType::Int16(*nodata),
1282 InMemoryRasterData::UInt16 { nodata, .. } => PixType::UInt16(*nodata),
1283 InMemoryRasterData::Int32 { nodata, .. } => PixType::Int32(*nodata),
1284 InMemoryRasterData::UInt32 { nodata, .. } => PixType::UInt32(*nodata),
1285 InMemoryRasterData::Float32 { nodata, .. } => PixType::Float32(*nodata),
1286 InMemoryRasterData::Float64 { nodata, .. } => PixType::Float64(*nodata),
1287 }
1288 }
1289}
1290
1291impl RasterDataSource {
1292
1293 fn to_wkb_string_big_endian(self) -> Vec<u8> {
1295
1296 use self::RasterDataSource::*;
1297 use crate::big_endian::*;
1298
1299 let mut s = Vec::new();
1300
1301 match self {
1302 Offline(OfflineRasterData { band, path, .. }) => {
1303 write_i8_be(&mut s, band);
1305 let path: Vec<u8> = path.as_os_str().to_string_lossy().as_bytes().to_vec();
1307 let cstring = unsafe { CString::from_vec_unchecked(path) };
1308 for byte in cstring.to_bytes_with_nul() {
1309 write_u8_be(&mut s, *byte);
1310 }
1311 },
1312 InMemory(data) => {
1313 match data {
1314 InMemoryRasterData::Bool1Bit { data, .. } => { for row in data { for byte in row { write_bool_be(&mut s, byte); } } },
1315 InMemoryRasterData::UInt2 { data, .. } => { for row in data { for byte in row { write_u8_be(&mut s, byte); } } },
1316 InMemoryRasterData::UInt4 { data, .. } => { for row in data { for byte in row { write_u8_be(&mut s, byte); } } },
1317 InMemoryRasterData::Int8 { data, .. } => { for row in data { for byte in row { write_i8_be(&mut s, byte); } } },
1318 InMemoryRasterData::UInt8 { data, .. } => { for row in data { for byte in row { write_u8_be(&mut s, byte); } } },
1319 InMemoryRasterData::Int16 { data, .. } => { for row in data { for byte in row { write_i16_be(&mut s, byte); } } },
1320 InMemoryRasterData::UInt16 { data, .. } => { for row in data { for byte in row { write_u16_be(&mut s, byte); } } },
1321 InMemoryRasterData::Int32 { data, .. } => { for row in data { for byte in row { write_i32_be(&mut s, byte); } } },
1322 InMemoryRasterData::UInt32 { data, .. } => { for row in data { for byte in row { write_u32_be(&mut s, byte); } } },
1323 InMemoryRasterData::Float32 { data, .. } => { for row in data { for byte in row { write_f32_be(&mut s, byte); } } },
1324 InMemoryRasterData::Float64 { data, .. } => { for row in data { for byte in row { write_f64_be(&mut s, byte); } } },
1325 }
1326 },
1327 }
1328
1329 s
1330 }
1331
1332 fn to_wkb_string_little_endian(self) -> Vec<u8> {
1334
1335 use self::RasterDataSource::*;
1336 use self::little_endian::*;
1337
1338 let mut s = Vec::new();
1339
1340 match self {
1341 Offline(OfflineRasterData { band, path, .. }) => {
1342 write_i8_le(&mut s, band);
1344 let path: Vec<u8> = path.as_os_str().to_string_lossy().as_bytes().to_vec();
1346 let cstring = unsafe { CString::from_vec_unchecked(path) };
1347 for byte in cstring.into_bytes_with_nul() {
1348 let byte: u8 = byte; write_u8_le(&mut s, byte);
1350 }
1351 },
1352 InMemory(data) => {
1353 match data {
1354 InMemoryRasterData::Bool1Bit { data, .. } => { for row in data { for byte in row { write_bool_le(&mut s, byte); } } },
1355 InMemoryRasterData::UInt2 { data, .. } => { for row in data { for byte in row { write_u8_le(&mut s, byte); } } },
1356 InMemoryRasterData::UInt4 { data, .. } => { for row in data { for byte in row { write_u8_le(&mut s, byte); } } },
1357 InMemoryRasterData::Int8 { data, .. } => { for row in data { for byte in row { write_i8_le(&mut s, byte); } } },
1358 InMemoryRasterData::UInt8 { data, .. } => { for row in data { for byte in row { write_u8_le(&mut s, byte); } } },
1359 InMemoryRasterData::Int16 { data, .. } => { for row in data { for byte in row { write_i16_le(&mut s, byte); } } },
1360 InMemoryRasterData::UInt16 { data, .. } => { for row in data { for byte in row { write_u16_le(&mut s, byte); } } },
1361 InMemoryRasterData::Int32 { data, .. } => { for row in data { for byte in row { write_i32_le(&mut s, byte); } } },
1362 InMemoryRasterData::UInt32 { data, .. } => { for row in data { for byte in row { write_u32_le(&mut s, byte); } } },
1363 InMemoryRasterData::Float32 { data, .. } => { for row in data { for byte in row { write_f32_le(&mut s, byte); } } },
1364 InMemoryRasterData::Float64 { data, .. } => { for row in data { for byte in row { write_f64_le(&mut s, byte); } } },
1365 }
1366 },
1367 }
1368
1369 s
1370 }
1371}