block/include/nil/crypto3/detail/pack.hpp
Go to the documentation of this file.
1 //---------------------------------------------------------------------------//
2 // Copyright (c) 2018-2020 Mikhail Komarov <nemo@nil.foundation>
3 // Copyright (c) 2020 Alexander Sokolov <asokolov@nil.foundation>
4 //
5 // MIT License
6 //
7 // Permission is hereby granted, free of charge, to any person obtaining a copy
8 // of this software and associated documentation files (the "Software"), to deal
9 // in the Software without restriction, including without limitation the rights
10 // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11 // copies of the Software, and to permit persons to whom the Software is
12 // furnished to do so, subject to the following conditions:
13 //
14 // The above copyright notice and this permission notice shall be included in all
15 // copies or substantial portions of the Software.
16 //
17 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20 // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21 // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22 // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23 // SOFTWARE.
24 //---------------------------------------------------------------------------//
25 
26 #ifndef CRYPTO3_DETAIL_PACK_HPP
27 #define CRYPTO3_DETAIL_PACK_HPP
28 
29 #include <nil/crypto3/detail/type_traits.hpp>
30 #include <nil/crypto3/detail/stream_endian.hpp>
31 #include <nil/crypto3/detail/exploder.hpp>
32 #include <nil/crypto3/detail/imploder.hpp>
33 #include <nil/crypto3/detail/reverser.hpp>
34 #include <nil/crypto3/detail/predef.hpp>
35 
36 #include <boost/static_assert.hpp>
37 #include <boost/predef/other/endian.h>
38 #include <boost/predef/architecture.h>
39 
40 #include <algorithm>
41 #include <climits>
42 #include <iterator>
43 #include <type_traits>
44 
45 namespace nil {
46  namespace crypto3 {
47  namespace detail {
48 
70  template<int UnitBits, int InputBits, int OutputBits, typename InT, typename OutT>
71  struct host_can_memcpy {
72  constexpr static const bool value = !(UnitBits % CHAR_BIT) && InputBits >= UnitBits &&
73  OutputBits >= UnitBits && sizeof(InT) * CHAR_BIT == InputBits &&
74  sizeof(OutT) * CHAR_BIT == OutputBits;
75  };
76 
89  template<typename Endianness, int InputBits, int OutputBits, typename InT, typename OutT>
90  struct can_memcpy {
91  constexpr static const bool value = InputBits == OutputBits && sizeof(InT) == sizeof(OutT);
92  };
93 
94  template<int UnitBits, int InputBits, int OutputBits, typename InT, typename OutT>
95  struct can_memcpy<stream_endian::host_unit<UnitBits>, InputBits, OutputBits, InT, OutT>
96  : host_can_memcpy<UnitBits, InputBits, OutputBits, InT, OutT> { };
97 
98 #ifdef BOOST_ENDIAN_LITTLE_BYTE_AVAILABLE
99  template<int UnitBits, int InputBits, int OutputBits, typename InT, typename OutT>
100  struct can_memcpy<stream_endian::little_unit_big_bit<UnitBits>, InputBits, OutputBits, InT, OutT>
101  : host_can_memcpy<UnitBits, InputBits, OutputBits, InT, OutT> { };
102 
103  template<int UnitBits, int InputBits, int OutputBits, typename InT, typename OutT>
104  struct can_memcpy<stream_endian::little_unit_little_bit<UnitBits>, InputBits, OutputBits, InT, OutT>
105  : host_can_memcpy<UnitBits, InputBits, OutputBits, InT, OutT> { };
106 
107 #elif defined(BOOST_ENDIAN_BIG_BYTE_AVAILABLE)
108  template<int UnitBits, int InputBits, int OutputBits, typename InT, typename OutT>
109  struct can_memcpy<stream_endian::big_unit_big_bit<UnitBits>, ValueBits, InT, OutT>
110  : host_can_memcpy<UnitBits, InputBits, OutputBits, InT, OutT> { };
111  template<int UnitBits, int InputBits, int OutputBits, typename InT, typename OutT>
112  struct can_memcpy<stream_endian::big_unit_little_bit<UnitBits>, ValueBits, InT, OutT>
113  : host_can_memcpy<UnitBits, InputBits, OutputBits, , InT, OutT> { };
114 #endif
115 
139  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
140  std::size_t OutputValueBits, typename InputType, typename OutputType,
141  bool SameEndianness = std::is_same<InputEndianness, OutputEndianness>::value,
142  bool Implode = (InputValueBits < OutputValueBits),
143  bool Explode = (InputValueBits > OutputValueBits)>
144  struct real_packer { };
145 
160  template<typename Endianness, std::size_t ValueBits, typename InputType, typename OutputType>
161  struct real_packer<Endianness, Endianness, ValueBits, ValueBits, InputType, OutputType, true, false,
162  false> {
176  template<std::size_t InputValueBits, std::size_t OutputValueBits>
177  inline static typename std::enable_if<
179  pack_n(InputType const *in, std::size_t n, OutputType *out) {
180  std::memcpy(out, in, n * sizeof(InputType));
181  }
182 
195  template<std::size_t InputValueBits, std::size_t OutputValueBits>
196  inline static typename std::enable_if<
198  pack_n(InputType *in, std::size_t n, OutputType *out) {
199  std::memcpy(out, in, n * sizeof(InputType));
200  }
201 
216  template<typename InputIterator, typename OutputIterator>
217  inline static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out) {
218  std::copy(in, in + in_n, out);
219  }
220 
239  template<typename InputIterator, typename OutputIterator>
240  inline static void pack(InputIterator first, InputIterator last, std::random_access_iterator_tag,
241  OutputIterator out, std::random_access_iterator_tag) {
242  pack_n(first, std::distance(first, last), out);
243  }
244 
265  template<typename InputIterator, typename InCatT, typename OutputIterator, typename OutCatT>
266  inline static void pack(InputIterator first, InputIterator last, InCatT, OutputIterator out, OutCatT) {
267  std::copy(first, last, out);
268  }
269 
284  template<typename InputIterator, typename OutputIterator>
285  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
286 
287  typedef typename std::iterator_traits<InputIterator>::iterator_category in_cat;
288  typedef typename std::iterator_traits<OutputIterator>::iterator_category out_cat;
289 
290  pack(first, last, in_cat(), out, out_cat());
291  }
292  };
293 
310  template<int UnitBits, template<int> class InputEndian, template<int> class OutputEndian,
311  std::size_t ValueBits, typename InputType, typename OutputType>
312  struct real_packer<InputEndian<UnitBits>, OutputEndian<UnitBits>, ValueBits, ValueBits, InputType,
313  OutputType, false, false, false> {
314 
315  typedef InputEndian<UnitBits> InputEndianness;
316  typedef OutputEndian<UnitBits> OutputEndianness;
317 
320 
321  template<typename InputIterator, typename OutputIterator>
322  inline static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out) {
323 
324  std::transform(in, in + in_n, out, [](InputType const &elem) {
326  });
327  }
328 
329  template<typename InputIterator, typename OutputIterator>
330  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
331 
332  std::transform(first, last, out, [](InputType const &elem) {
334  });
335  }
336  };
337 
354  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
355  std::size_t OutputValueBits, typename InputType, typename OutputType, bool SameEndianness>
356  struct real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
357  OutputType, SameEndianness, true, false> {
358 
359  BOOST_STATIC_ASSERT(!(OutputValueBits % InputValueBits));
360 
361  typedef nil::crypto3::detail::imploder<InputEndianness, OutputEndianness, InputValueBits,
362  OutputValueBits>
364 
365  template<typename InputIterator, typename OutputIterator>
366  inline static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out) {
367  std::size_t out_n = in_n / (OutputValueBits / InputValueBits);
368 
369  while (out_n--) {
370  OutputType value = OutputType();
371  imploder::implode(in, value);
372  *out++ = value;
373  }
374  }
375 
376  template<typename InputIterator, typename OutputIterator>
377  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
378  while (first != last) {
379  OutputType value = OutputType();
380  imploder::implode(first, value);
381  *out++ = value;
382  }
383  }
384  };
385 
402  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
403  std::size_t OutputValueBits, typename InputType, typename OutputType, bool SameEndianness>
404  struct real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
405  OutputType, SameEndianness, false, true> {
406 
407  BOOST_STATIC_ASSERT(!(InputValueBits % OutputValueBits));
408 
409  typedef nil::crypto3::detail::exploder<InputEndianness, OutputEndianness, InputValueBits,
410  OutputValueBits>
412 
413  template<typename InputIterator, typename OutputIterator>
414  inline static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out) {
415  while (in_n--) {
416  InputType const value = *in++;
417  exploder::explode(value, out);
418  }
419  }
420 
421  template<typename InputIterator, typename OutputIterator>
422  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
423  while (first != last) {
424  InputType const value = *first++;
425  exploder::explode(value, out);
426  }
427  }
428  };
429 
442  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
443  std::size_t OutputValueBits, typename InputType, typename OutputType>
444  struct packer {
445 
446  template<typename InputIterator, typename OutputIterator>
447  inline static void pack_n(InputIterator in, std::size_t n, OutputIterator out) {
448  typedef real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
449  OutputType>
450  packer_type;
451 
452  packer_type::pack_n(in, n, out);
453  }
454 
455  template<typename InputIterator, typename OutputIterator>
456  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
457  typedef real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
458  OutputType>
459  packer_type;
460 
461  packer_type::pack(first, last, out);
462  }
463  };
464 
475  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
476  std::size_t OutputValueBits>
477  struct packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, bool, bool> {
478 
479  template<typename InputIterator, typename OutputIterator>
480  inline static void pack_n(InputIterator in, std::size_t n, OutputIterator out) {
482  packer_type;
483 
484  packer_type::pack_n(in, n, out);
485  }
486 
487  template<typename InputIterator, typename OutputIterator>
488  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
490  packer_type;
491 
492  packer_type::pack(first, last, out);
493  }
494  };
495 
507  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
508  std::size_t OutputValueBits, typename OutputType>
509  struct packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, bool, OutputType> {
510 
511  template<typename InputIterator, typename OutputIterator>
512  inline static void pack_n(InputIterator in, std::size_t n, OutputIterator out) {
513  typedef real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, bool,
514  OutputType>
515  packer_type;
516 
517  packer_type::pack_n(in, n, out);
518  }
519 
520  template<typename InputIterator, typename OutputIterator>
521  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
522  typedef real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, bool,
523  OutputType>
524  packer_type;
525 
526  packer_type::pack(first, last, out);
527  }
528  };
529 
541  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
542  std::size_t OutputValueBits, typename InputType>
543  struct packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType, bool> {
544 
545  template<typename InputIterator, typename OutputIterator>
546  inline static void pack_n(InputIterator in, std::size_t n, OutputIterator out) {
547  typedef real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
548  bool>
549  packer_type;
550 
551  packer_type::pack_n(in, n, out);
552  }
553 
554  template<typename InputIterator, typename OutputIterator>
555  inline static void pack(InputIterator first, InputIterator last, OutputIterator out) {
556  typedef real_packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
557  bool>
558  packer_type;
559 
560  packer_type::pack(first, last, out);
561  }
562  };
563 
582  template<typename OutputEndianness, std::size_t InputValueBits, std::size_t OutputValueBits,
583  typename InputIterator, typename OutputIterator>
584  inline void pack_to(InputIterator first, InputIterator last, OutputIterator out) {
585 
586  typedef typename std::iterator_traits<InputIterator>::value_type InputType;
587  typedef typename std::iterator_traits<OutputIterator>::value_type OutputType;
588 
589 #ifdef BOOST_ENDIAN_BIG_BYTE_AVAILABLE
590  typedef packer<stream_endian::big_octet_big_bit, OutputEndianness, InputValueBits, OutputValueBits,
591  InputType, OutputType>
592  packer_type;
593 #elif defined(BOOST_ENDIAN_LITTLE_BYTE_AVAILABLE)
594  typedef packer<stream_endian::little_octet_big_bit, OutputEndianness, InputValueBits, OutputValueBits,
595  InputType, OutputType>
596  packer_type;
597 #elif defined(BOOST_ENDIAN_BIG_WORD_AVAILABLE)
599  InputValueBits, OutputValueBits, InputType, OutputType>
600  packer_type;
601 #elif defined(BOOST_ENDIAN_LITTLE_WORD_AVAILABLE)
603  InputValueBits, OutputValueBits, InputType, OutputType>
604  packer_type;
605 #else
606 #error "Unknown endianness"
607 #endif
608 
609  packer_type::pack(first, last, out);
610  }
611 
630  template<typename InputEndianness, std::size_t InputValueBits, std::size_t OutputValueBits,
631  typename InputIterator, typename OutputIterator>
632  inline void pack_from(InputIterator first, InputIterator last, OutputIterator out) {
633 
634  typedef typename std::iterator_traits<InputIterator>::value_type InputType;
635  typedef typename std::iterator_traits<OutputIterator>::value_type OutputType;
636 
637 #ifdef BOOST_ENDIAN_BIG_BYTE_AVAILABLE
638  typedef packer<InputEndianness, stream_endian::big_octet_big_bit, InputValueBits, OutputValueBits,
639  InputType, OutputType>
640  packer_type;
641 #elif defined(BOOST_ENDIAN_LITTLE_BYTE_AVAILABLE)
642  typedef packer<InputEndianness, stream_endian::little_octet_big_bit, InputValueBits, OutputValueBits,
643  InputType, OutputType>
644  packer_type;
645 #elif defined(BOOST_ENDIAN_BIG_WORD_AVAILABLE)
647  InputValueBits, OutputValueBits, InputType, OutputType>
648  packer_type;
649 #elif defined(BOOST_ENDIAN_LITTLE_WORD_AVAILABLE)
651  InputValueBits, OutputValueBits, InputType, OutputType>
652  packer_type;
653 #else
654 #error "Unknown endianness"
655 #endif
656 
657  packer_type::pack(first, last, out);
658  }
659 
678  template<typename OutputEndianness, std::size_t InputValueBits, std::size_t OutputValueBits,
679  typename InputRange, typename OutputIterator>
680  inline void pack_to(const InputRange &r, OutputIterator out) {
681 
682  typedef typename std::iterator_traits<typename InputRange::iterator>::value_type InputType;
683  typedef typename std::iterator_traits<OutputIterator>::value_type OutputType;
684 
685 #ifdef BOOST_ENDIAN_BIG_BYTE_AVAILABLE
686  typedef packer<stream_endian::big_octet_big_bit, OutputEndianness, InputValueBits, OutputValueBits,
687  InputType, OutputType>
688  packer_type;
689 #elif defined(BOOST_ENDIAN_LITTLE_BYTE_AVAILABLE)
690  typedef packer<stream_endian::little_octet_big_bit, OutputEndianness, InputValueBits, OutputValueBits,
691  InputType, OutputType>
692  packer_type;
693 #elif defined(BOOST_ENDIAN_BIG_WORD_AVAILABLE)
695  InputValueBits, OutputValueBits, InputType, OutputType>
696  packer_type;
697 #elif defined(BOOST_ENDIAN_LITTLE_WORD_AVAILABLE)
699  InputValueBits, OutputValueBits, InputType, OutputType>
700  packer_type;
701 #else
702 #error "Unknown endianness"
703 #endif
704 
705  packer_type::pack(std::begin(r), std::end(r), out);
706  }
707 
726  template<typename InputEndianness, std::size_t InputValueBits, std::size_t OutputValueBits,
727  typename InputRange, typename OutputIterator>
728  inline void pack_from(const InputRange &r, OutputIterator out) {
729 
730  typedef typename std::iterator_traits<typename InputRange::iterator>::value_type InputType;
731  typedef typename std::iterator_traits<OutputIterator>::value_type OutputType;
732 
733 #ifdef BOOST_ENDIAN_BIG_BYTE_AVAILABLE
734  typedef packer<InputEndianness, stream_endian::big_octet_big_bit, InputValueBits, OutputValueBits,
735  InputType, OutputType>
736  packer_type;
737 #elif defined(BOOST_ENDIAN_LITTLE_BYTE_AVAILABLE)
738  typedef packer<InputEndianness, stream_endian::little_octet_big_bit, InputValueBits, OutputValueBits,
739  InputType, OutputType>
740  packer_type;
741 #elif defined(BOOST_ENDIAN_BIG_WORD_AVAILABLE)
743  InputValueBits, OutputValueBits, InputType, OutputType>
744  packer_type;
745 #elif defined(BOOST_ENDIAN_LITTLE_WORD_AVAILABLE)
747  InputValueBits, OutputValueBits, InputType, OutputType>
748  packer_type;
749 #else
750 #error "Unknown endianness"
751 #endif
752 
753  packer_type::pack(std::begin(r), std::end(r), out);
754  }
755 
774  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
775  std::size_t OutputValueBits, typename InputIterator, typename OutputIterator>
776  inline void pack_n(InputIterator in, std::size_t in_n, OutputIterator out) {
777  typedef typename std::iterator_traits<InputIterator>::value_type InputType;
778  typedef typename std::iterator_traits<OutputIterator>::value_type OutputType;
779  typedef packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
780  OutputType>
781  packer_type;
782 
783  packer_type::pack_n(in, in_n, out);
784  }
785 
805  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
806  std::size_t OutputValueBits, typename InputIterator, typename OutputIterator>
807  inline void pack_n(InputIterator in, std::size_t in_n, OutputIterator out, std::size_t out_n) {
808  BOOST_ASSERT(in_n * InputValueBits == out_n * OutputValueBits);
809 
810  pack_n<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(in, in_n, out);
811  }
812 
833  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
834  std::size_t OutputValueBits, typename InputIterator, typename OutputIterator>
835  inline void pack(InputIterator first, InputIterator last, std::random_access_iterator_tag,
836  OutputIterator out) {
837  pack_n<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(first, last - first, out);
838  }
839 
862  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
863  std::size_t OutputValueBits, typename InputIterator, typename InCatT, typename OutputIterator,
864  typename = typename std::enable_if<nil::crypto3::detail::is_iterator<InputIterator>::value>::type,
865  typename = typename std::enable_if<nil::crypto3::detail::is_iterator<OutputIterator>::value>::type>
866  inline void pack(InputIterator first, InputIterator last, InCatT, OutputIterator out) {
867  typedef typename std::iterator_traits<InputIterator>::value_type InputType;
868  typedef typename std::iterator_traits<OutputIterator>::value_type OutputType;
869  typedef packer<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits, InputType,
870  OutputType>
871  packer_type;
872 
873  packer_type::pack(first, last, out);
874  }
875 
894  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
895  std::size_t OutputValueBits, typename InputIterator, typename OutputIterator,
896  typename = typename std::enable_if<nil::crypto3::detail::is_iterator<OutputIterator>::value>::type>
897  inline void pack(InputIterator first, InputIterator last, OutputIterator out) {
898  typedef typename std::iterator_traits<InputIterator>::iterator_category in_cat;
899 
900  pack<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(first, last, in_cat(), out);
901  }
902 
925  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
926  std::size_t OutputValueBits, typename InputIterator, typename OutputIterator>
927  inline void pack(InputIterator in_first, InputIterator in_last, std::random_access_iterator_tag,
928  OutputIterator out_first, OutputIterator out_last, std::random_access_iterator_tag) {
929  pack_n<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(
930  in_first, in_last - in_first, out_first, out_last - out_first);
931  }
932 
958  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
959  std::size_t OutputValueBits, typename InputIterator, typename InCatT, typename OutputIterator,
960  typename OutCatT>
961  inline void pack(InputIterator in_first, InputIterator in_last, InCatT, OutputIterator out, OutputIterator,
962  OutCatT) {
963  pack<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(in_first, in_last, out);
964  }
965 
985  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
986  std::size_t OutputValueBits, typename InputIterator, typename OutputIterator>
987  inline void pack(InputIterator in_first, InputIterator in_last, OutputIterator out_first,
988  OutputIterator out_last) {
989  typedef typename std::iterator_traits<InputIterator>::iterator_category in_cat;
990  typedef typename std::iterator_traits<OutputIterator>::iterator_category out_cat;
991 
992  pack<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(
993  in_first, in_last, in_cat(), out_first, out_last, out_cat());
994  }
995 
1013  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
1014  std::size_t OutputValueBits, typename InputType, typename OutputType>
1015  inline void pack(const InputType &in, OutputType &out) {
1016  pack_n<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(in.begin(), in.size(),
1017  out.begin(), out.size());
1018  }
1019 
1038  template<typename InputEndianness, typename OutputEndianness, std::size_t InputValueBits,
1039  std::size_t OutputValueBits, typename InputIterator, typename OutputType,
1040  typename = typename std::enable_if<!std::is_arithmetic<OutputType>::value>::type>
1041  inline void pack(InputIterator first, InputIterator last, OutputType &out) {
1042  pack_n<InputEndianness, OutputEndianness, InputValueBits, OutputValueBits>(
1043  first, std::distance(first, last), out.begin(), out.size());
1044  }
1045 
1046  } // namespace detail
1047  } // namespace crypto3
1048 } // namespace nil
1049 
1050 #endif // CRYPTO3_DETAIL_PACK_HPP
void pack_n(InputIterator in, std::size_t in_n, OutputIterator out)
Packs in_n input elements starting from in into output elements beginning from out.
Definition: block/include/nil/crypto3/detail/pack.hpp:776
static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out)
Packs in_n elements iterated by in into elements iterated by out.
Definition: block/include/nil/crypto3/detail/pack.hpp:217
void pack_n(InputIterator in, std::size_t in_n, OutputIterator out, std::size_t out_n)
Packs in_n input elements starting from in into in_out elements beginning from out.
Definition: block/include/nil/crypto3/detail/pack.hpp:807
static std::enable_if< can_memcpy< Endianness, InputValueBits, OutputValueBits, InputType, OutputType >::value >::type pack_n(InputType *in, std::size_t n, OutputType *out)
Packs n InputType elements pointed by pointer in into OutType elements pointed by out....
Definition: block/include/nil/crypto3/detail/pack.hpp:198
void pack(InputIterator first, InputIterator last, OutputType &out)
Packs elements from range [first, last) into data referenced by out with non-arithmetic value type.
Definition: block/include/nil/crypto3/detail/pack.hpp:1041
void pack_from(InputIterator first, InputIterator last, OutputIterator out)
Packs elements from range [first, last) represented in InputEndianness endianness into elements start...
Definition: block/include/nil/crypto3/detail/pack.hpp:632
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Generic function that chooses pack function depending on input and output iterator category.
Definition: block/include/nil/crypto3/detail/pack.hpp:285
void pack_to(InputIterator first, InputIterator last, OutputIterator out)
Packs elements from range [first, last) represented in machine-dependent endianness into elements sta...
Definition: block/include/nil/crypto3/detail/pack.hpp:584
void pack(InputIterator first, InputIterator last, std::random_access_iterator_tag, OutputIterator out)
Packs elements from the range [first, last) into elements starting from out. Works for input containe...
Definition: block/include/nil/crypto3/detail/pack.hpp:835
static void pack(InputIterator first, InputIterator last, InCatT, OutputIterator out, OutCatT)
Packs elements in range [first, last) into elements iterated by out. This function is invoked only if...
Definition: block/include/nil/crypto3/detail/pack.hpp:266
static std::enable_if< can_memcpy< Endianness, InputValueBits, OutputValueBits, InputType, OutputType >::value >::type pack_n(InputType const *in, std::size_t n, OutputType *out)
Packs n InputType elements pointed by constant pointer in (which, hence, cannot be iterated) into Out...
Definition: block/include/nil/crypto3/detail/pack.hpp:179
static void pack(InputIterator first, InputIterator last, std::random_access_iterator_tag, OutputIterator out, std::random_access_iterator_tag)
Packs elements in range [first, last) into elements iterated by out. This function is invoked only if...
Definition: block/include/nil/crypto3/detail/pack.hpp:240
decoded_range< UnaryFunction, SinglePassRange > transform(SinglePassRange &rng, UnaryFunction fn)
Definition: decrypted.hpp:100
void reverse(Range &a, std::size_t n)
Definition: basic_operations.hpp:54
little_unit_big_bit< 8 > little_octet_big_bit
Definition: algebra/include/nil/crypto3/detail/stream_endian.hpp:65
big_unit_big_bit< 8 > big_octet_big_bit
Definition: algebra/include/nil/crypto3/detail/stream_endian.hpp:55
Definition: pair.hpp:31
bit_reverser reverses the sequence of bits in each unit of the given value, if InputEndianness and Ou...
Definition: block/include/nil/crypto3/detail/reverser.hpp:266
can_memcpy trait is derived from host_can_memcpy trait and is invoked depending on data endianness....
Definition: block/include/nil/crypto3/detail/pack.hpp:90
constexpr static const bool value
Definition: block/include/nil/crypto3/detail/pack.hpp:91
exploder forms a sequence of output values represented in OutputEndianness endianness from an input v...
Definition: block/include/nil/crypto3/detail/exploder.hpp:148
The group of traits below is used to determine the possibility of fast data copy. By fast data copy w...
Definition: block/include/nil/crypto3/detail/pack.hpp:71
constexpr static const bool value
Definition: block/include/nil/crypto3/detail/pack.hpp:72
imploder processes a sequence of input values represented in InputEndianness endianness into an outpu...
Definition: block/include/nil/crypto3/detail/imploder.hpp:122
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:488
static void pack_n(InputIterator in, std::size_t n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:480
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:521
static void pack_n(InputIterator in, std::size_t n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:512
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:555
static void pack_n(InputIterator in, std::size_t n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:546
This packer deals with arbitrary input and output (but not bool) data elements.
Definition: block/include/nil/crypto3/detail/pack.hpp:444
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:456
static void pack_n(InputIterator in, std::size_t n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:447
unit_reverser< InputEndianness, OutputEndianness, UnitBits > units_reverser
Definition: block/include/nil/crypto3/detail/pack.hpp:318
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:330
bit_reverser< InputEndianness, OutputEndianness, UnitBits > bits_reverser
Definition: block/include/nil/crypto3/detail/pack.hpp:319
static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:322
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:377
nil::crypto3::detail::imploder< InputEndianness, OutputEndianness, InputValueBits, OutputValueBits > imploder
Definition: block/include/nil/crypto3/detail/pack.hpp:363
static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:366
nil::crypto3::detail::exploder< InputEndianness, OutputEndianness, InputValueBits, OutputValueBits > exploder
Definition: block/include/nil/crypto3/detail/pack.hpp:411
static void pack_n(InputIterator in, std::size_t in_n, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:414
static void pack(InputIterator first, InputIterator last, OutputIterator out)
Definition: block/include/nil/crypto3/detail/pack.hpp:422
Real_packer is used to transform input data divided into chunks of the bit size InputValueBits repres...
Definition: block/include/nil/crypto3/detail/pack.hpp:144
unit_reverser reverses the sequence of units in the given value, if InputEndianness and OutputEndiann...
Definition: block/include/nil/crypto3/detail/reverser.hpp:423