secret.c 4.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151
  1. /*
  2. * QEMU crypto secret support
  3. *
  4. * Copyright (c) 2015 Red Hat, Inc.
  5. *
  6. * This library is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU Lesser General Public
  8. * License as published by the Free Software Foundation; either
  9. * version 2.1 of the License, or (at your option) any later version.
  10. *
  11. * This library 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 GNU
  14. * Lesser General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU Lesser General Public
  17. * License along with this library; if not, see <http://www.gnu.org/licenses/>.
  18. *
  19. */
  20. #include "qemu/osdep.h"
  21. #include "crypto/secret.h"
  22. #include "qapi/error.h"
  23. #include "qom/object_interfaces.h"
  24. #include "qemu/module.h"
  25. #include "trace.h"
  26. static void
  27. qcrypto_secret_load_data(QCryptoSecretCommon *sec_common,
  28. uint8_t **output,
  29. size_t *outputlen,
  30. Error **errp)
  31. {
  32. char *data = NULL;
  33. size_t length = 0;
  34. GError *gerr = NULL;
  35. QCryptoSecret *secret = QCRYPTO_SECRET(sec_common);
  36. *output = NULL;
  37. *outputlen = 0;
  38. if (secret->file) {
  39. if (secret->data) {
  40. error_setg(errp,
  41. "'file' and 'data' are mutually exclusive");
  42. return;
  43. }
  44. if (!g_file_get_contents(secret->file, &data, &length, &gerr)) {
  45. error_setg(errp,
  46. "Unable to read %s: %s",
  47. secret->file, gerr->message);
  48. g_error_free(gerr);
  49. return;
  50. }
  51. *output = (uint8_t *)data;
  52. *outputlen = length;
  53. } else if (secret->data) {
  54. *outputlen = strlen(secret->data);
  55. *output = (uint8_t *)g_strdup(secret->data);
  56. } else {
  57. error_setg(errp, "Either 'file' or 'data' must be provided");
  58. }
  59. }
  60. static void
  61. qcrypto_secret_prop_set_data(Object *obj,
  62. const char *value,
  63. Error **errp)
  64. {
  65. QCryptoSecret *secret = QCRYPTO_SECRET(obj);
  66. g_free(secret->data);
  67. secret->data = g_strdup(value);
  68. }
  69. static char *
  70. qcrypto_secret_prop_get_data(Object *obj,
  71. Error **errp)
  72. {
  73. QCryptoSecret *secret = QCRYPTO_SECRET(obj);
  74. return g_strdup(secret->data);
  75. }
  76. static void
  77. qcrypto_secret_prop_set_file(Object *obj,
  78. const char *value,
  79. Error **errp)
  80. {
  81. QCryptoSecret *secret = QCRYPTO_SECRET(obj);
  82. g_free(secret->file);
  83. secret->file = g_strdup(value);
  84. }
  85. static char *
  86. qcrypto_secret_prop_get_file(Object *obj,
  87. Error **errp)
  88. {
  89. QCryptoSecret *secret = QCRYPTO_SECRET(obj);
  90. return g_strdup(secret->file);
  91. }
  92. static void
  93. qcrypto_secret_finalize(Object *obj)
  94. {
  95. QCryptoSecret *secret = QCRYPTO_SECRET(obj);
  96. g_free(secret->file);
  97. g_free(secret->data);
  98. }
  99. static void
  100. qcrypto_secret_class_init(ObjectClass *oc, void *data)
  101. {
  102. QCryptoSecretCommonClass *sic = QCRYPTO_SECRET_COMMON_CLASS(oc);
  103. sic->load_data = qcrypto_secret_load_data;
  104. object_class_property_add_str(oc, "data",
  105. qcrypto_secret_prop_get_data,
  106. qcrypto_secret_prop_set_data);
  107. object_class_property_add_str(oc, "file",
  108. qcrypto_secret_prop_get_file,
  109. qcrypto_secret_prop_set_file);
  110. }
  111. static const TypeInfo qcrypto_secret_info = {
  112. .parent = TYPE_QCRYPTO_SECRET_COMMON,
  113. .name = TYPE_QCRYPTO_SECRET,
  114. .instance_size = sizeof(QCryptoSecret),
  115. .instance_finalize = qcrypto_secret_finalize,
  116. .class_size = sizeof(QCryptoSecretClass),
  117. .class_init = qcrypto_secret_class_init,
  118. };
  119. static void
  120. qcrypto_secret_register_types(void)
  121. {
  122. type_register_static(&qcrypto_secret_info);
  123. }
  124. type_init(qcrypto_secret_register_types);