s3.c 7.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174
  1. /**
  2. * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
  3. * SPDX-License-Identifier: Apache-2.0.
  4. */
  5. #include <aws/s3/s3.h>
  6. #include <aws/auth/auth.h>
  7. #include <aws/common/error.h>
  8. #include <aws/common/hash_table.h>
  9. #include <aws/http/http.h>
  10. #define AWS_DEFINE_ERROR_INFO_S3(CODE, STR) AWS_DEFINE_ERROR_INFO(CODE, STR, "aws-c-s3")
  11. /* clang-format off */
  12. static struct aws_error_info s_errors[] = {
  13. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_MISSING_CONTENT_RANGE_HEADER, "Response missing required Content-Range header."),
  14. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_INVALID_CONTENT_RANGE_HEADER, "Response contains invalid Content-Range header."),
  15. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_MISSING_CONTENT_LENGTH_HEADER, "Response missing required Content-Length header."),
  16. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_INVALID_CONTENT_LENGTH_HEADER, "Response contains invalid Content-Length header."),
  17. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_MISSING_ETAG, "Response missing required ETag header."),
  18. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_INTERNAL_ERROR, "Response code indicates internal server error"),
  19. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_SLOW_DOWN, "Response code indicates throttling"),
  20. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_INVALID_RESPONSE_STATUS, "Invalid response status from request"),
  21. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_MISSING_UPLOAD_ID, "Upload Id not found in create-multipart-upload response"),
  22. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_PROXY_PARSE_FAILED, "Could not parse proxy URI"),
  23. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_UNSUPPORTED_PROXY_SCHEME, "Given Proxy URI has an unsupported scheme"),
  24. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_CANCELED, "Request successfully cancelled"),
  25. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_INVALID_RANGE_HEADER, "Range header has invalid syntax"),
  26. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_MULTIRANGE_HEADER_UNSUPPORTED, "Range header specifies multiple ranges which is unsupported"),
  27. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_RESPONSE_CHECKSUM_MISMATCH, "response checksum header does not match calculated checksum"),
  28. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_CHECKSUM_CALCULATION_FAILED, "failed to calculate a checksum for the provided stream"),
  29. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_PAUSED, "Request successfully paused"),
  30. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_LIST_PARTS_PARSE_FAILED, "Failed to parse result from list parts"),
  31. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_RESUMED_PART_CHECKSUM_MISMATCH, "Checksum does not match previously uploaded part"),
  32. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_RESUME_FAILED, "Resuming request failed"),
  33. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_OBJECT_MODIFIED, "The object modifed during download."),
  34. AWS_DEFINE_ERROR_INFO_S3(AWS_ERROR_S3_NON_RECOVERABLE_ASYNC_ERROR, "Async error received from S3 and not recoverable from retry.")
  35. };
  36. /* clang-format on */
  37. static struct aws_error_info_list s_error_list = {
  38. .error_list = s_errors,
  39. .count = AWS_ARRAY_SIZE(s_errors),
  40. };
  41. static struct aws_log_subject_info s_s3_log_subject_infos[] = {
  42. DEFINE_LOG_SUBJECT_INFO(AWS_LS_S3_GENERAL, "S3General", "Subject for aws-c-s3 logging that defies categorization."),
  43. DEFINE_LOG_SUBJECT_INFO(AWS_LS_S3_CLIENT, "S3Client", "Subject for aws-c-s3 logging from an aws_s3_client."),
  44. DEFINE_LOG_SUBJECT_INFO(
  45. AWS_LS_S3_CLIENT_STATS,
  46. "S3ClientStats",
  47. "Subject for aws-c-s3 logging for stats tracked by an aws_s3_client."),
  48. DEFINE_LOG_SUBJECT_INFO(AWS_LS_S3_REQUEST, "S3Request", "Subject for aws-c-s3 logging from an aws_s3_request."),
  49. DEFINE_LOG_SUBJECT_INFO(
  50. AWS_LS_S3_META_REQUEST,
  51. "S3MetaRequest",
  52. "Subject for aws-c-s3 logging from an aws_s3_meta_request."),
  53. DEFINE_LOG_SUBJECT_INFO(AWS_LS_S3_ENDPOINT, "S3Endpoint", "Subject for aws-c-s3 logging from an aws_s3_endpoint."),
  54. };
  55. static struct aws_log_subject_info_list s_s3_log_subject_list = {
  56. .subject_list = s_s3_log_subject_infos,
  57. .count = AWS_ARRAY_SIZE(s_s3_log_subject_infos),
  58. };
  59. /**** Configuration info for the c5n.18xlarge *****/
  60. static struct aws_byte_cursor s_c5n_18xlarge_nic_array[] = {AWS_BYTE_CUR_INIT_FROM_STRING_LITERAL("eth0")};
  61. static struct aws_s3_cpu_group_info s_c5n_18xlarge_cpu_group_info_array[] = {
  62. {
  63. .cpu_group = 0u,
  64. .nic_name_array = s_c5n_18xlarge_nic_array,
  65. .nic_name_array_length = AWS_ARRAY_SIZE(s_c5n_18xlarge_nic_array),
  66. },
  67. {
  68. .cpu_group = 1u,
  69. .nic_name_array = NULL,
  70. .nic_name_array_length = 0u,
  71. },
  72. };
  73. static struct aws_s3_compute_platform_info s_c5n_18xlarge_platform_info = {
  74. .instance_type = AWS_BYTE_CUR_INIT_FROM_STRING_LITERAL("c5n.18xlarge"),
  75. .max_throughput_gbps = 100u,
  76. .cpu_group_info_array = s_c5n_18xlarge_cpu_group_info_array,
  77. .cpu_group_info_array_length = AWS_ARRAY_SIZE(s_c5n_18xlarge_cpu_group_info_array),
  78. };
  79. /****** End c5n.18xlarge *****/
  80. static struct aws_hash_table s_compute_platform_info_table;
  81. static bool s_library_initialized = false;
  82. static struct aws_allocator *s_library_allocator = NULL;
  83. void aws_s3_library_init(struct aws_allocator *allocator) {
  84. if (s_library_initialized) {
  85. return;
  86. }
  87. if (allocator) {
  88. s_library_allocator = allocator;
  89. } else {
  90. s_library_allocator = aws_default_allocator();
  91. }
  92. aws_auth_library_init(s_library_allocator);
  93. aws_http_library_init(s_library_allocator);
  94. aws_register_error_info(&s_error_list);
  95. aws_register_log_subject_info_list(&s_s3_log_subject_list);
  96. AWS_FATAL_ASSERT(
  97. !aws_hash_table_init(
  98. &s_compute_platform_info_table,
  99. allocator,
  100. 32,
  101. aws_hash_byte_cursor_ptr_ignore_case,
  102. (bool (*)(const void *, const void *))aws_byte_cursor_eq_ignore_case,
  103. NULL,
  104. NULL) &&
  105. "Hash table init failed!");
  106. AWS_FATAL_ASSERT(
  107. !aws_hash_table_put(
  108. &s_compute_platform_info_table,
  109. &s_c5n_18xlarge_platform_info.instance_type,
  110. &s_c5n_18xlarge_platform_info,
  111. NULL) &&
  112. "hash table put failed!");
  113. s_library_initialized = true;
  114. }
  115. void aws_s3_library_clean_up(void) {
  116. if (!s_library_initialized) {
  117. return;
  118. }
  119. s_library_initialized = false;
  120. aws_thread_join_all_managed();
  121. aws_hash_table_clean_up(&s_compute_platform_info_table);
  122. aws_unregister_log_subject_info_list(&s_s3_log_subject_list);
  123. aws_unregister_error_info(&s_error_list);
  124. aws_http_library_clean_up();
  125. aws_auth_library_clean_up();
  126. s_library_allocator = NULL;
  127. }
  128. struct aws_s3_compute_platform_info *aws_s3_get_compute_platform_info_for_instance_type(
  129. const struct aws_byte_cursor instance_type_name) {
  130. AWS_LOGF_TRACE(
  131. AWS_LS_S3_GENERAL,
  132. "static: looking up compute platform info for instance type " PRInSTR,
  133. AWS_BYTE_CURSOR_PRI(instance_type_name));
  134. struct aws_hash_element *platform_info_element = NULL;
  135. aws_hash_table_find(&s_compute_platform_info_table, &instance_type_name, &platform_info_element);
  136. if (platform_info_element) {
  137. AWS_LOGF_INFO(
  138. AWS_LS_S3_GENERAL,
  139. "static: found compute platform info for instance type " PRInSTR,
  140. AWS_BYTE_CURSOR_PRI(instance_type_name));
  141. return platform_info_element->value;
  142. }
  143. AWS_LOGF_INFO(
  144. AWS_LS_S3_GENERAL,
  145. "static: compute platform info for instance type " PRInSTR " not found",
  146. AWS_BYTE_CURSOR_PRI(instance_type_name));
  147. return NULL;
  148. }