diff options
author | Yash Tibrewal <yashkt@google.com> | 2017-09-21 18:56:08 -0700 |
---|---|---|
committer | Yash Tibrewal <yashkt@google.com> | 2017-10-02 16:29:41 -0700 |
commit | 83062842c3601faeddcae8f901c515e3c78f3661 (patch) | |
tree | 58536b25350a5f2b3123161ab4ca9b8ce01a43a5 /src/core/lib/transport/service_config.c | |
parent | 1c9b584a153ff592c92b6cf6baa620d8602a37cd (diff) |
Changes for C to C++. Adding extern C to header files for compatibility.
Also converting to .cc
Diffstat (limited to 'src/core/lib/transport/service_config.c')
-rw-r--r-- | src/core/lib/transport/service_config.c | 246 |
1 files changed, 0 insertions, 246 deletions
diff --git a/src/core/lib/transport/service_config.c b/src/core/lib/transport/service_config.c deleted file mode 100644 index 070a13a2b4..0000000000 --- a/src/core/lib/transport/service_config.c +++ /dev/null @@ -1,246 +0,0 @@ -// -// Copyright 2015 gRPC authors. -// -// Licensed under the Apache License, Version 2.0 (the "License"); -// you may not use this file except in compliance with the License. -// You may obtain a copy of the License at -// -// http://www.apache.org/licenses/LICENSE-2.0 -// -// Unless required by applicable law or agreed to in writing, software -// distributed under the License is distributed on an "AS IS" BASIS, -// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -// See the License for the specific language governing permissions and -// limitations under the License. -// - -#include "src/core/lib/transport/service_config.h" - -#include <string.h> - -#include <grpc/impl/codegen/grpc_types.h> -#include <grpc/support/alloc.h> -#include <grpc/support/log.h> -#include <grpc/support/string_util.h> - -#include "src/core/lib/json/json.h" -#include "src/core/lib/slice/slice_hash_table.h" -#include "src/core/lib/slice/slice_internal.h" -#include "src/core/lib/slice/slice_string_helpers.h" -#include "src/core/lib/support/string.h" - -// The main purpose of the code here is to parse the service config in -// JSON form, which will look like this: -// -// { -// "loadBalancingPolicy": "string", // optional -// "methodConfig": [ // array of one or more method_config objects -// { -// "name": [ // array of one or more name objects -// { -// "service": "string", // required -// "method": "string", // optional -// } -// ], -// // remaining fields are optional. -// // see https://developers.google.com/protocol-buffers/docs/proto3#json -// // for format details. -// "waitForReady": bool, -// "timeout": "duration_string", -// "maxRequestMessageBytes": "int64_string", -// "maxResponseMessageBytes": "int64_string", -// } -// ] -// } - -struct grpc_service_config { - char* json_string; // Underlying storage for json_tree. - grpc_json* json_tree; -}; - -grpc_service_config* grpc_service_config_create(const char* json_string) { - grpc_service_config* service_config = - (grpc_service_config*)gpr_malloc(sizeof(*service_config)); - service_config->json_string = gpr_strdup(json_string); - service_config->json_tree = - grpc_json_parse_string(service_config->json_string); - if (service_config->json_tree == NULL) { - gpr_log(GPR_INFO, "failed to parse JSON for service config"); - gpr_free(service_config->json_string); - gpr_free(service_config); - return NULL; - } - return service_config; -} - -void grpc_service_config_destroy(grpc_service_config* service_config) { - grpc_json_destroy(service_config->json_tree); - gpr_free(service_config->json_string); - gpr_free(service_config); -} - -void grpc_service_config_parse_global_params( - const grpc_service_config* service_config, - void (*process_json)(const grpc_json* json, void* arg), void* arg) { - const grpc_json* json = service_config->json_tree; - if (json->type != GRPC_JSON_OBJECT || json->key != NULL) return; - for (grpc_json* field = json->child; field != NULL; field = field->next) { - if (field->key == NULL) return; - if (strcmp(field->key, "methodConfig") == 0) continue; - process_json(field, arg); - } -} - -const char* grpc_service_config_get_lb_policy_name( - const grpc_service_config* service_config) { - const grpc_json* json = service_config->json_tree; - if (json->type != GRPC_JSON_OBJECT || json->key != NULL) return NULL; - const char* lb_policy_name = NULL; - for (grpc_json* field = json->child; field != NULL; field = field->next) { - if (field->key == NULL) return NULL; - if (strcmp(field->key, "loadBalancingPolicy") == 0) { - if (lb_policy_name != NULL) return NULL; // Duplicate. - if (field->type != GRPC_JSON_STRING) return NULL; - lb_policy_name = field->value; - } - } - return lb_policy_name; -} - -// Returns the number of names specified in the method config \a json. -static size_t count_names_in_method_config_json(grpc_json* json) { - size_t num_names = 0; - for (grpc_json* field = json->child; field != NULL; field = field->next) { - if (field->key != NULL && strcmp(field->key, "name") == 0) ++num_names; - } - return num_names; -} - -// Returns a path string for the JSON name object specified by \a json. -// Returns NULL on error. Caller takes ownership of result. -static char* parse_json_method_name(grpc_json* json) { - if (json->type != GRPC_JSON_OBJECT) return NULL; - const char* service_name = NULL; - const char* method_name = NULL; - for (grpc_json* child = json->child; child != NULL; child = child->next) { - if (child->key == NULL) return NULL; - if (child->type != GRPC_JSON_STRING) return NULL; - if (strcmp(child->key, "service") == 0) { - if (service_name != NULL) return NULL; // Duplicate. - if (child->value == NULL) return NULL; - service_name = child->value; - } else if (strcmp(child->key, "method") == 0) { - if (method_name != NULL) return NULL; // Duplicate. - if (child->value == NULL) return NULL; - method_name = child->value; - } - } - if (service_name == NULL) return NULL; // Required field. - char* path; - gpr_asprintf(&path, "/%s/%s", service_name, - method_name == NULL ? "*" : method_name); - return path; -} - -// Parses the method config from \a json. Adds an entry to \a entries for -// each name found, incrementing \a idx for each entry added. -// Returns false on error. -static bool parse_json_method_config( - grpc_exec_ctx* exec_ctx, grpc_json* json, - void* (*create_value)(const grpc_json* method_config_json), - grpc_slice_hash_table_entry* entries, size_t* idx) { - // Construct value. - void* method_config = create_value(json); - if (method_config == NULL) return false; - // Construct list of paths. - bool success = false; - gpr_strvec paths; - gpr_strvec_init(&paths); - for (grpc_json* child = json->child; child != NULL; child = child->next) { - if (child->key == NULL) continue; - if (strcmp(child->key, "name") == 0) { - if (child->type != GRPC_JSON_ARRAY) goto done; - for (grpc_json* name = child->child; name != NULL; name = name->next) { - char* path = parse_json_method_name(name); - gpr_strvec_add(&paths, path); - } - } - } - if (paths.count == 0) goto done; // No names specified. - // Add entry for each path. - for (size_t i = 0; i < paths.count; ++i) { - entries[*idx].key = grpc_slice_from_copied_string(paths.strs[i]); - entries[*idx].value = method_config; - ++*idx; - } - success = true; -done: - gpr_strvec_destroy(&paths); - return success; -} - -grpc_slice_hash_table* grpc_service_config_create_method_config_table( - grpc_exec_ctx* exec_ctx, const grpc_service_config* service_config, - void* (*create_value)(const grpc_json* method_config_json), - void (*destroy_value)(grpc_exec_ctx* exec_ctx, void* value)) { - const grpc_json* json = service_config->json_tree; - // Traverse parsed JSON tree. - if (json->type != GRPC_JSON_OBJECT || json->key != NULL) return NULL; - size_t num_entries = 0; - grpc_slice_hash_table_entry* entries = NULL; - for (grpc_json* field = json->child; field != NULL; field = field->next) { - if (field->key == NULL) return NULL; - if (strcmp(field->key, "methodConfig") == 0) { - if (entries != NULL) return NULL; // Duplicate. - if (field->type != GRPC_JSON_ARRAY) return NULL; - // Find number of entries. - for (grpc_json* method = field->child; method != NULL; - method = method->next) { - num_entries += count_names_in_method_config_json(method); - } - // Populate method config table entries. - entries = (grpc_slice_hash_table_entry*)gpr_malloc( - num_entries * sizeof(grpc_slice_hash_table_entry)); - size_t idx = 0; - for (grpc_json* method = field->child; method != NULL; - method = method->next) { - if (!parse_json_method_config(exec_ctx, method, create_value, entries, - &idx)) { - return NULL; - } - } - GPR_ASSERT(idx == num_entries); - } - } - // Instantiate method config table. - grpc_slice_hash_table* method_config_table = NULL; - if (entries != NULL) { - method_config_table = - grpc_slice_hash_table_create(num_entries, entries, destroy_value, NULL); - gpr_free(entries); - } - return method_config_table; -} - -void* grpc_method_config_table_get(grpc_exec_ctx* exec_ctx, - const grpc_slice_hash_table* table, - grpc_slice path) { - void* value = grpc_slice_hash_table_get(table, path); - // If we didn't find a match for the path, try looking for a wildcard - // entry (i.e., change "/service/method" to "/service/*"). - if (value == NULL) { - char* path_str = grpc_slice_to_c_string(path); - const char* sep = strrchr(path_str, '/') + 1; - const size_t len = (size_t)(sep - path_str); - char* buf = (char*)gpr_malloc(len + 2); // '*' and NUL - memcpy(buf, path_str, len); - buf[len] = '*'; - buf[len + 1] = '\0'; - grpc_slice wildcard_path = grpc_slice_from_copied_string(buf); - gpr_free(buf); - value = grpc_slice_hash_table_get(table, wildcard_path); - grpc_slice_unref_internal(exec_ctx, wildcard_path); - gpr_free(path_str); - } - return value; -} |