tr.c 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127
  1. /* tr.c -- The tr command. */
  2. /*
  3. * GRUB -- GRand Unified Bootloader
  4. * Copyright (C) 2010,2013 Free Software Foundation, Inc.
  5. *
  6. * GRUB is free software: you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation, either version 3 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * GRUB is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. * GNU General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with GRUB. If not, see <http://www.gnu.org/licenses/>.
  18. */
  19. #include <grub/dl.h>
  20. #include <grub/mm.h>
  21. #include <grub/err.h>
  22. #include <grub/env.h>
  23. #include <grub/i18n.h>
  24. #include <grub/misc.h>
  25. #include <grub/extcmd.h>
  26. GRUB_MOD_LICENSE ("GPLv3+");
  27. static const struct grub_arg_option options[] =
  28. {
  29. { "set", 's', 0, N_("Set a variable to return value."), N_("VARNAME"), ARG_TYPE_STRING },
  30. { "upcase", 'U', 0, N_("Translate to upper case."), 0, 0 },
  31. { "downcase", 'D', 0, N_("Translate to lower case."), 0, 0 },
  32. { 0, 0, 0, 0, 0, 0 }
  33. };
  34. static const char *letters_lowercase = "abcdefghijklmnopqrstuvwxyz";
  35. static const char *letters_uppercase = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
  36. static grub_err_t
  37. grub_cmd_tr (grub_extcmd_context_t ctxt, int argc, char **args)
  38. {
  39. char *var = 0;
  40. const char *input = 0;
  41. char *output = 0, *optr;
  42. const char *s1 = 0;
  43. const char *s2 = 0;
  44. const char *iptr;
  45. /* Select the defaults from options. */
  46. if (ctxt->state[0].set) {
  47. var = ctxt->state[0].arg;
  48. input = grub_env_get (var);
  49. }
  50. if (ctxt->state[1].set) {
  51. s1 = letters_lowercase;
  52. s2 = letters_uppercase;
  53. }
  54. if (ctxt->state[2].set) {
  55. s1 = letters_uppercase;
  56. s2 = letters_lowercase;
  57. }
  58. /* Check for arguments and update the defaults. */
  59. if (argc == 1)
  60. input = args[0];
  61. else if (argc == 2) {
  62. s1 = args[0];
  63. s2 = args[1];
  64. } else if (argc == 3) {
  65. s1 = args[0];
  66. s2 = args[1];
  67. input = args[2];
  68. } else if (argc > 3)
  69. return grub_error (GRUB_ERR_BAD_ARGUMENT, "too many parameters");
  70. if (!s1 || !s2 || !input)
  71. return grub_error (GRUB_ERR_BAD_ARGUMENT, "missing parameters");
  72. if (grub_strlen (s1) != grub_strlen (s2))
  73. return grub_error (GRUB_ERR_BAD_ARGUMENT, "set sizes did not match");
  74. /* Translate input into output buffer. */
  75. output = grub_malloc (grub_strlen (input) + 1);
  76. if (! output)
  77. return grub_errno;
  78. optr = output;
  79. for (iptr = input; *iptr; iptr++)
  80. {
  81. char *p = grub_strchr (s1, *iptr);
  82. if (p)
  83. *optr++ = s2[p - s1];
  84. else
  85. *optr++ = *iptr;
  86. }
  87. *optr = '\0';
  88. if (ctxt->state[0].set)
  89. grub_env_set (var, output);
  90. else
  91. grub_printf ("%s\n", output);
  92. grub_free (output);
  93. return GRUB_ERR_NONE;
  94. }
  95. static grub_extcmd_t cmd;
  96. GRUB_MOD_INIT(tr)
  97. {
  98. cmd = grub_register_extcmd ("tr", grub_cmd_tr, 0, N_("[OPTIONS] [SET1] [SET2] [STRING]"),
  99. N_("Translate SET1 characters to SET2 in STRING."), options);
  100. }
  101. GRUB_MOD_FINI(tr)
  102. {
  103. grub_unregister_extcmd (cmd);
  104. }