1 /*
2 * Copyright (C) 2018-2019 Alexander Borisov
3 *
4 * Author: Alexander Borisov <borisov@lexbor.com>
5 */
6
7 #include "lexbor/tag/tag.h"
8
9 #include "lexbor/tag/res.h"
10
11
12 LXB_API const lxb_tag_data_t *
lxb_tag_append(lexbor_hash_t * hash,lxb_tag_id_t tag_id,const lxb_char_t * name,size_t length)13 lxb_tag_append(lexbor_hash_t *hash, lxb_tag_id_t tag_id,
14 const lxb_char_t *name, size_t length)
15 {
16 lxb_tag_data_t *data;
17 const lexbor_shs_entry_t *entry;
18
19 entry = lexbor_shs_entry_get_static(lxb_tag_res_shs_data_default,
20 name, length);
21 if (entry != NULL) {
22 return entry->value;
23 }
24
25 data = lexbor_hash_insert(hash, lexbor_hash_insert_raw, name, length);
26 if (data == NULL) {
27 return NULL;
28 }
29
30 if (tag_id == LXB_TAG__UNDEF) {
31 data->tag_id = (lxb_tag_id_t) data;
32 }
33 else {
34 data->tag_id = tag_id;
35 }
36
37 return data;
38 }
39
40 LXB_API const lxb_tag_data_t *
lxb_tag_append_lower(lexbor_hash_t * hash,const lxb_char_t * name,size_t length)41 lxb_tag_append_lower(lexbor_hash_t *hash, const lxb_char_t *name, size_t length)
42 {
43 lxb_tag_data_t *data;
44 const lexbor_shs_entry_t *entry;
45
46 entry = lexbor_shs_entry_get_lower_static(lxb_tag_res_shs_data_default,
47 name, length);
48 if (entry != NULL) {
49 return entry->value;
50 }
51
52 data = lexbor_hash_insert(hash, lexbor_hash_insert_lower, name, length);
53 if (data == NULL) {
54 return NULL;
55 }
56
57 data->tag_id = (lxb_tag_id_t) data;
58
59 return data;
60 }
61
62 const lxb_tag_data_t *
lxb_tag_data_by_id(lexbor_hash_t * hash,lxb_tag_id_t tag_id)63 lxb_tag_data_by_id(lexbor_hash_t *hash, lxb_tag_id_t tag_id)
64 {
65 if (tag_id >= LXB_TAG__LAST_ENTRY) {
66 if (tag_id == LXB_TAG__LAST_ENTRY) {
67 return NULL;
68 }
69
70 return (const lxb_tag_data_t *) tag_id;
71 }
72
73 return &lxb_tag_res_data_default[tag_id];
74 }
75
76 const lxb_tag_data_t *
lxb_tag_data_by_name(lexbor_hash_t * hash,const lxb_char_t * name,size_t len)77 lxb_tag_data_by_name(lexbor_hash_t *hash, const lxb_char_t *name, size_t len)
78 {
79 const lexbor_shs_entry_t *entry;
80
81 if (name == NULL || len == 0) {
82 return NULL;
83 }
84
85 entry = lexbor_shs_entry_get_lower_static(lxb_tag_res_shs_data_default,
86 name, len);
87 if (entry != NULL) {
88 return (const lxb_tag_data_t *) entry->value;
89 }
90
91 return (const lxb_tag_data_t *) lexbor_hash_search(hash,
92 lexbor_hash_search_lower, name, len);
93 }
94
95 #if 0
96 const lxb_tag_data_t *
97 lxb_tag_data_by_name_upper(lexbor_hash_t *hash,
98 const lxb_char_t *name, size_t len)
99 {
100 uintptr_t dif;
101 const lexbor_shs_entry_t *entry;
102
103 if (name == NULL || len == 0) {
104 return NULL;
105 }
106
107 entry = lexbor_shs_entry_get_upper_static(lxb_tag_res_shs_data_default,
108 name, len);
109 if (entry != NULL) {
110 dif = (const lxb_tag_data_t *) entry->value - lxb_tag_res_data_default;
111
112 return (const lxb_tag_data_t *) (lxb_tag_res_data_upper_default + dif);
113 }
114
115 return (const lxb_tag_data_t *) lexbor_hash_search(hash,
116 lexbor_hash_search_upper, name, len);
117 }
118 #endif
119
120 /*
121 * No inline functions for ABI.
122 */
123 const lxb_char_t *
lxb_tag_name_by_id_noi(lexbor_hash_t * hash,lxb_tag_id_t tag_id,size_t * len)124 lxb_tag_name_by_id_noi(lexbor_hash_t *hash, lxb_tag_id_t tag_id, size_t *len)
125 {
126 return lxb_tag_name_by_id(hash, tag_id, len);
127 }
128
129 const lxb_char_t *
lxb_tag_name_upper_by_id_noi(lexbor_hash_t * hash,lxb_tag_id_t tag_id,size_t * len)130 lxb_tag_name_upper_by_id_noi(lexbor_hash_t *hash,
131 lxb_tag_id_t tag_id, size_t *len)
132 {
133 return lxb_tag_name_upper_by_id(hash, tag_id, len);
134 }
135
136 lxb_tag_id_t
lxb_tag_id_by_name_noi(lexbor_hash_t * hash,const lxb_char_t * name,size_t len)137 lxb_tag_id_by_name_noi(lexbor_hash_t *hash, const lxb_char_t *name, size_t len)
138 {
139 return lxb_tag_id_by_name(hash, name, len);
140 }
141
142 lexbor_mraw_t *
lxb_tag_mraw_noi(lexbor_hash_t * hash)143 lxb_tag_mraw_noi(lexbor_hash_t *hash)
144 {
145 return lxb_tag_mraw(hash);
146 }
147