gnunet-base32.c 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152
  1. /*
  2. This file is part of GNUnet.
  3. Copyright (C) 2021 GNUnet e.V.
  4. GNUnet is free software: you can redistribute it and/or modify it
  5. under the terms of the GNU Affero General Public License as published
  6. by the Free Software Foundation, either version 3 of the License,
  7. or (at your option) any later version.
  8. GNUnet is distributed in the hope that it will be useful, but
  9. WITHOUT ANY WARRANTY; without even the implied warranty of
  10. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  11. Affero General Public License for more details.
  12. You should have received a copy of the GNU Affero General Public License
  13. along with this program. If not, see <http://www.gnu.org/licenses/>.
  14. SPDX-License-Identifier: AGPL3.0-or-later
  15. */
  16. /**
  17. * @file util/gnunet-base32.c
  18. * @brief tool to encode/decode from/to the Crockford Base32 encoding GNUnet uses
  19. * @author Christian Grothoff
  20. */
  21. #include "platform.h"
  22. #include "gnunet_util_lib.h"
  23. /**
  24. * The main function of gnunet-base32
  25. *
  26. * @param argc number of arguments from the command line
  27. * @param argv command line arguments
  28. * @return 0 ok, 1 on error
  29. */
  30. int
  31. main (int argc,
  32. char *const *argv)
  33. {
  34. int decode = 0;
  35. const struct GNUNET_GETOPT_CommandLineOption options[] = {
  36. GNUNET_GETOPT_option_flag ('d',
  37. "decode",
  38. gettext_noop ("run decoder modus, otherwise runs as encoder"),
  39. &decode),
  40. GNUNET_GETOPT_option_help ("Crockford base32 encoder/decoder"),
  41. GNUNET_GETOPT_option_version (PACKAGE_VERSION),
  42. GNUNET_GETOPT_OPTION_END
  43. };
  44. int ret;
  45. char *in;
  46. unsigned int in_size;
  47. ssize_t iret;
  48. char *out;
  49. size_t out_size;
  50. if (GNUNET_OK !=
  51. GNUNET_STRINGS_get_utf8_args (argc, argv,
  52. &argc, &argv))
  53. return 2;
  54. ret = GNUNET_GETOPT_run ("gnunet-base32",
  55. options,
  56. argc,
  57. argv);
  58. if (ret < 0)
  59. return 1;
  60. if (0 == ret)
  61. return 0;
  62. in_size = 0;
  63. in = NULL;
  64. iret = 1;
  65. while (iret > 0)
  66. {
  67. /* read in blocks of 4k */
  68. char buf[4092];
  69. iret = read (0,
  70. buf,
  71. sizeof (buf));
  72. if (iret < 0)
  73. {
  74. GNUNET_free (in);
  75. return 2;
  76. }
  77. if (iret > 0)
  78. {
  79. if (iret + in_size < in_size)
  80. {
  81. GNUNET_break (0);
  82. GNUNET_free (in);
  83. return 1;
  84. }
  85. GNUNET_array_grow (in,
  86. in_size,
  87. in_size + iret);
  88. memcpy (&in[in_size - iret],
  89. buf,
  90. iret);
  91. }
  92. }
  93. if (decode)
  94. {
  95. /* This formula can overestimate by 1 byte, so we try both
  96. out_size and out_size-1 below */
  97. out_size = in_size * 5 / 8;
  98. out = GNUNET_malloc (out_size);
  99. if (GNUNET_OK !=
  100. GNUNET_STRINGS_string_to_data (in,
  101. in_size,
  102. out,
  103. out_size))
  104. {
  105. out_size--;
  106. if (GNUNET_OK !=
  107. GNUNET_STRINGS_string_to_data (in,
  108. in_size,
  109. out,
  110. out_size))
  111. {
  112. GNUNET_free (out);
  113. GNUNET_free (in);
  114. return 3;
  115. }
  116. }
  117. }
  118. else
  119. {
  120. out = GNUNET_STRINGS_data_to_string_alloc (in,
  121. in_size);
  122. out_size = strlen (out);
  123. }
  124. {
  125. size_t pos = 0;
  126. while (pos < out_size)
  127. {
  128. iret = write (1,
  129. &out[pos],
  130. out_size - pos);
  131. if (iret <= 0)
  132. return 4;
  133. pos += iret;
  134. }
  135. }
  136. GNUNET_free (out);
  137. GNUNET_free_nz ((void *) argv);
  138. return 0;
  139. }
  140. /* end of gnunet-uri.c */