DS3 C SDK  4.1.0
Provides access to the Spectra S3 API with C
ds3_string_multimap.c
Go to the documentation of this file.
1 /*
2  * ******************************************************************************
3  * Copyright 2014-2017 Spectra Logic Corporation. All Rights Reserved.
4  * Licensed under the Apache License, Version 2.0 (the "License"). You may not use
5  * this file except in compliance with the License. A copy of the License is located at
6  *
7  * http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * or in the "license" file accompanying this file.
10  * This file is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
11  * CONDITIONS OF ANY KIND, either express or implied. See the License for the
12  * specific language governing permissions and limitations under the License.
13  * ****************************************************************************
14  */
15 
16 #include <glib.h>
17 #include "ds3.h"
18 #include "ds3_string_multimap.h"
20 
21 static void _free_pointer_array(gpointer pointer) {
22  GPtrArray* array = (GPtrArray*) pointer;
23 
24  g_ptr_array_free(array, TRUE);
25 }
26 
27 /* This is used to free the entires in the values ptr array in the ds3_string_multimap_entry
28  */
29 static void _internal_str_free(gpointer data) {
30  ds3_str_free((ds3_str*)data);
31 }
32 
33 // hashify the string rather than the ds3_str* for better distribution
34 static guint _ds3_str_hash(gconstpointer key) {
35  if (key == NULL) return 0;
36 
37  const ds3_str* d_str = (const ds3_str*)key;
38  return g_str_hash(d_str->value);
39 }
40 
41 static gboolean _ds3_str_equal(gconstpointer a, gconstpointer b) {
42  if ((a == NULL) || (b == NULL)) return FALSE;
43 
44  const ds3_str* _a = (const ds3_str*) a;
45  const ds3_str* _b = (const ds3_str*) b;
46 
47  return g_str_equal(_a->value, _b->value);
48 }
49 
51  struct _ds3_string_multimap* multimap = g_new0(struct _ds3_string_multimap, 1);
52  multimap->hash = g_hash_table_new_full(_ds3_str_hash, _ds3_str_equal, _internal_str_free, _free_pointer_array);
53 
54  return (ds3_string_multimap*) multimap;
55 }
56 
57 void ds3_string_multimap_insert(ds3_string_multimap* map, const ds3_str* key, const ds3_str* value) {
58  struct _ds3_string_multimap* _map = (struct _ds3_string_multimap*) map;
59  GPtrArray* entries = g_hash_table_lookup(_map->hash, key);
60  if (entries == NULL) {
61  entries = g_ptr_array_new_with_free_func(_internal_str_free);
62  g_hash_table_insert(_map->hash, ds3_str_dup(key), entries);
63  }
64  g_ptr_array_add(entries, ds3_str_dup(value));
65 }
66 
67 // Add an entry (key & 1+ values) to a map
68 // caller frees all passed in values
70  if ((map == NULL) || (entry == NULL)) return;
71 
72  int index;
73  int num_values = ds3_string_multimap_entry_get_num_values(entry);
75  for (index = 0; index < num_values; index++) {
77  ds3_string_multimap_insert(map, key, value);
78  ds3_str_free(value);
79  }
80  ds3_str_free(key);
81 }
82 
83 // caller frees returned ds3_string_multimap_entry
85  if ((map == NULL) || (key == NULL)) return NULL;
86 
87  struct _ds3_string_multimap* _map = (struct _ds3_string_multimap*)map;
88  GPtrArray* values = g_hash_table_lookup(_map->hash, key);
89  if (values == NULL) return NULL;
90 
92  unsigned int index;
93  unsigned int num_values = values->len;
94  for (index=0; index < num_values; index++) {
95  ds3_str* current_value = g_ptr_array_index(values, index);
96  ds3_string_multimap_entry_add_value(entry, current_value);
97  }
98 
99  return entry;
100 }
101 
103  if (map == NULL) return;
104 
105  struct _ds3_string_multimap* _map = (struct _ds3_string_multimap*) map;
106  if (_map->hash != NULL) {
107  g_hash_table_destroy(_map->hash);
108  }
109 
110  g_free(map);
111 }
112 
113 
114 // The following functions manipulate ds3_string_multimap_entry
115 
116 // caller frees returned ds3_string_multimap_entry
118  struct _ds3_string_multimap_entry* _entry = g_new0(ds3_string_multimap_entry, 1);
119  _entry->key = ds3_str_dup(key);
120  _entry->values = g_ptr_array_new_with_free_func(_internal_str_free);
121  return (ds3_string_multimap_entry*)_entry;
122 }
123 
125  if ((entry == NULL) || (value == NULL)) return;
126 
127  struct _ds3_string_multimap_entry* _entry = entry;
128  g_ptr_array_add(_entry->values, (gpointer)ds3_str_dup(value));
129 }
130 
131 // caller frees returned ds3_string_multimap_entry
133  const struct _ds3_string_multimap_entry* _entry = entry;
135  unsigned int index;
136  unsigned int num_values = ds3_string_multimap_entry_get_num_values(entry);
137  for (index = 0; index < num_values; index++) {
139  }
140 
141  return duped_entry;
142 }
143 
144 // caller frees returned ds3_str
146  const struct _ds3_string_multimap_entry* _entry = entry;
147  if (entry == NULL) {
148  return NULL;
149  }
150 
151  return ds3_str_dup(_entry->key);
152 }
153 
154 // caller frees returned ds3_str
156  const struct _ds3_string_multimap_entry* _entry = entry;
157  if ((entry == NULL) || (index > ds3_string_multimap_entry_get_num_values(entry))) {
158  return NULL;
159  }
160 
161  ds3_str* value = ds3_str_dup(g_ptr_array_index(_entry->values, index));
162  return value;
163 }
164 
166  if (map_entry == NULL) return 0;
167 
168  const struct _ds3_string_multimap_entry* _entry = map_entry;
169  return _entry->values->len;
170 }
171 
173  if (entry == NULL) {
174  return;
175  }
176 
177  struct _ds3_string_multimap_entry* _entry = (struct _ds3_string_multimap_entry*) entry;
178  ds3_str_free(_entry->key);
179  g_ptr_array_free(_entry->values, TRUE);
180  g_free(entry);
181 }
182 
ds3_str * key
ds3_string_multimap_entry * ds3_string_multimap_entry_init(const ds3_str *key)
static void _free_pointer_array(gpointer pointer)
GPtrArray * values
ds3_str * ds3_string_multimap_entry_get_value_by_index(const ds3_string_multimap_entry *entry, unsigned int index)
static void _internal_str_free(gpointer data)
ds3_string_multimap_entry * ds3_string_multimap_lookup(ds3_string_multimap *map, const ds3_str *key)
static gboolean _ds3_str_equal(gconstpointer a, gconstpointer b)
static guint _ds3_str_hash(gconstpointer key)
ds3_string_multimap_entry * ds3_string_multimap_entry_dup(const ds3_string_multimap_entry *entry)
void ds3_str_free(ds3_str *string)
Definition: ds3_string.c:50
ds3_str * ds3_str_dup(const ds3_str *string)
Definition: ds3_string.c:32
The public definitions for the Spectra S3 C SDK.
ds3_string_multimap * ds3_string_multimap_init(void)
unsigned int ds3_string_multimap_entry_get_num_values(const ds3_string_multimap_entry *map_entry)
void ds3_string_multimap_entry_add_value(ds3_string_multimap_entry *entry, const ds3_str *value)
void ds3_string_multimap_free(ds3_string_multimap *map)
void ds3_string_multimap_insert(ds3_string_multimap *map, const ds3_str *key, const ds3_str *value)
void ds3_string_multimap_entry_free(ds3_string_multimap_entry *entry)
ds3_str * ds3_string_multimap_entry_get_key(const ds3_string_multimap_entry *entry)
char * value
Definition: ds3_string.h:37
void ds3_string_multimap_insert_entry(ds3_string_multimap *map, const ds3_string_multimap_entry *entry)