YAZ 5.37.0
charneg.c
Go to the documentation of this file.
1/* This file is part of the YAZ toolkit.
2 * Copyright (C) Index Data
3 * See the file LICENSE for details.
4 */
11#if HAVE_CONFIG_H
12#include <config.h>
13#endif
14
15#include <stdio.h>
16#include <yaz/otherinfo.h>
17#include <yaz/z-charneg.h>
18#include <yaz/charneg.h>
19#include <yaz/yaz-util.h>
20#include <yaz/oid_db.h>
21#include <yaz/snprintf.h>
22
23static Z_External* z_ext_record2(ODR o, const char *buf)
24{
25 Z_External *p;
26 int len = strlen(buf);
27
28 if (!(p = (Z_External *)odr_malloc(o, sizeof(*p))))
29 return 0;
30 p->descriptor = 0;
31 p->indirect_reference = 0;
34 p->u.octet_aligned =
35 odr_create_Odr_oct(o, buf, len);
36 return p;
37}
38
39static int get_form(const char *charset)
40{
41 int form = -1;
42
43 if (!yaz_matchstr(charset, "UCS-2"))
44 form = 2;
45 if (!yaz_matchstr(charset, "UCS-4"))
46 form = 4;
47 if (!yaz_matchstr(charset, "UTF-16"))
48 form = 5;
49 if (!yaz_matchstr(charset, "UTF-8"))
50 form = 8;
51
52 return form;
53}
54
55static char *set_form(Odr_oid *encoding)
56{
57 static char *charset = 0;
58 if ( oid_oidlen(encoding) != 6)
59 return 0;
60 if (encoding[5] == 2)
61 charset = "UCS-2";
62 if (encoding[5] == 4)
63 charset = "UCS-4";
64 if (encoding[5] == 5)
65 charset = "UTF-16";
66 if (encoding[5] == 8)
67 charset = "UTF-8";
68 return charset;
69}
70
71static Z_OriginProposal_0 *z_get_OriginProposal_0(ODR o, const char *charset)
72{
73 int form = get_form(charset);
75 (Z_OriginProposal_0*)odr_malloc(o, sizeof(*p0));
76
77 memset(p0, 0, sizeof(*p0));
78
79 if (form > 0)
80 { /* ISO 10646 (UNICODE) */
81 char oidname[28];
82
83 Z_Iso10646 *is = (Z_Iso10646 *) odr_malloc(o, sizeof(*is));
85 p0->u.iso10646 = is;
86 is->collections = 0;
87 yaz_snprintf(oidname, sizeof(oidname), "1.0.10646.1.0.%d", form);
88 is->encodingLevel = odr_getoidbystr(o, oidname);
89 }
90 else
91 { /* private ones */
93 (Z_PrivateCharacterSet *)odr_malloc(o, sizeof(*pc));
94
95 memset(pc, 0, sizeof(*pc));
96
98 p0->u.zprivate = pc;
99
101 pc->u.externallySpecified = z_ext_record2(o, charset);
102 }
103 return p0;
104}
105
107 ODR o, const char **charsets, int num_charsets,
108 const char **langs, int num_langs, int selected)
109{
110 int i;
111 Z_OriginProposal *p = (Z_OriginProposal *) odr_malloc(o, sizeof(*p));
112
113 memset(p, 0, sizeof(*p));
114
116 *p->recordsInSelectedCharSets = (selected) ? 1 : 0;
117
118 if (charsets && num_charsets)
119 {
120 p->num_proposedCharSets = num_charsets;
123 odr_malloc(o, num_charsets*sizeof(Z_OriginProposal_0*));
124
125 for (i = 0; i < num_charsets; i++)
126 p->proposedCharSets[i] =
127 z_get_OriginProposal_0(o, charsets[i]);
128 }
129 if (langs && num_langs)
130 {
131 p->num_proposedlanguages = num_langs;
133 (char **) odr_malloc(o, num_langs*sizeof(char *));
134
135 for (i = 0; i < num_langs; i++)
136 p->proposedlanguages[i] = (char *)langs[i];
137 }
138 return p;
139}
140
142 ODR o)
143{
146
147 memset(p, 0, sizeof(*p));
148
149 return p;
150}
151
152/* Create EXTERNAL for negotation proposal. Client side */
154 const char **charsets, int num_charsets,
155 const char **langs, int num_langs,
156 int selected)
157{
158 Z_External *p = (Z_External *)odr_malloc(o, sizeof(*p));
159
160 p->descriptor = 0;
161 p->indirect_reference = 0;
162
164
168 p->u.charNeg3->u.proposal =
169 z_get_OriginProposal(o, charsets, num_charsets,
170 langs, num_langs, selected);
171
172 return p;
173}
174
176 const char *delim,
177 const char *charset_list,
178 const char *lang_list,
179 int selected)
180{
181 char **charsets_addresses = 0;
182 char **langs_addresses = 0;
183 int charsets_count = 0;
184 int langs_count = 0;
185
186 if (charset_list)
187 nmem_strsplit(odr_getmem(o), delim, charset_list,
188 &charsets_addresses, &charsets_count);
189 if (lang_list)
190 nmem_strsplit(odr_getmem(o), delim, lang_list,
191 &langs_addresses, &langs_count);
193 (const char **) charsets_addresses,
194 charsets_count,
195 (const char **) langs_addresses,
196 langs_count,
197 selected);
198}
199
200
201/* used by yaz_set_response_charneg */
202static Z_TargetResponse *z_get_TargetResponse(ODR o, const char *charset,
203 const char *lang, int selected)
204{
205 Z_TargetResponse *p = (Z_TargetResponse *) odr_malloc(o, sizeof(*p));
206 int form = get_form(charset);
207
208 memset(p, 0, sizeof(*p));
209 if (form > 0)
210 {
211 char oidname[28];
212
213 Z_Iso10646 *is = (Z_Iso10646 *) odr_malloc (o, sizeof(*is));
215 p->u.iso10646 = is;
216 is->collections = 0;
217 yaz_snprintf(oidname, sizeof oidname, "1.0.10646.1.0.%d", form);
218 is->encodingLevel = odr_getoidbystr (o, oidname);
219 }
220 else
221 {
223 (Z_PrivateCharacterSet *)odr_malloc(o, sizeof(*pc));
224
225 memset(pc, 0, sizeof(*pc));
226
228 p->u.zprivate = pc;
229
232 z_ext_record2(o, charset);
233 }
235 *p->recordsInSelectedCharSets = (selected) ? 1 : 0;
236
237 p->selectedLanguage = lang ? (char *) odr_strdup(o, lang) : 0;
238 return p;
239}
240
241/* Create charset response. Server side */
243 const char *lang, int selected)
244{
245 Z_External *p = (Z_External *)odr_malloc(o, sizeof(*p));
246
247 p->descriptor = 0;
248 p->indirect_reference = 0;
249
251
255 p->u.charNeg3->u.response = z_get_TargetResponse(o, charset, lang, selected);
256
257 return p;
258}
259
260/* Get negotiation from OtherInformation. Client&Server side */
262{
263 int i;
264
265 if (!p)
266 return 0;
267
268 for (i = 0; i < p->num_elements; i++)
269 {
270 Z_External *pext;
272 (pext = p->list[i]->information.externallyDefinedInfo))
273 {
276 {
277 return pext->u.charNeg3;
278 }
279 }
280 }
281 return 0;
282}
283
284/* Delete negotiation from OtherInformation. Client&Server side */
286{
287 int i;
288
289 if (!*p)
290 return 0;
291
292 for (i = 0; i < (*p)->num_elements; i++)
293 {
294 Z_External *pext;
295 if (((*p)->list[i]->which == Z_OtherInfo_externallyDefinedInfo) &&
296 (pext = (*p)->list[i]->information.externallyDefinedInfo))
297 {
300 {
301 if ((*p)->num_elements <= 1)
302 *p = 0;
303 else
304 {
305 --((*p)->num_elements);
306 for (; i < (*p)->num_elements; i++)
307 (*p)->list[i] = (*p)->list[i+1];
308 }
309 return 1;
310 }
311 }
312 }
313 return 0;
314}
315
316
317/* Get charsets, langs, selected from negotiation.. Server side */
319 char ***charsets, int *num_charsets,
320 char ***langs, int *num_langs, int *selected)
321{
322 int i;
323 Z_OriginProposal *pro = p->u.proposal;
324
325 if (num_charsets && charsets)
326 {
327 if (pro->num_proposedCharSets)
328 {
329 *num_charsets = pro->num_proposedCharSets;
330
331 (*charsets) = (char **)
332 nmem_malloc(mem, pro->num_proposedCharSets * sizeof(char *));
333
334 for (i = 0; i < pro->num_proposedCharSets; i++)
335 {
336 (*charsets)[i] = 0;
337
338 if (pro->proposedCharSets[i]->which ==
340 pro->proposedCharSets[i]->u.zprivate->which ==
342 {
343 Z_External *pext =
345
346 if (pext->which == Z_External_octet)
347 {
348 (*charsets)[i] = (char *)
349 nmem_malloc(mem, (1+pext->u.octet_aligned->len) *
350 sizeof(char));
351
352 memcpy((*charsets)[i], pext->u.octet_aligned->buf,
353 pext->u.octet_aligned->len);
354 (*charsets)[i][pext->u.octet_aligned->len] = 0;
355 }
356 }
357 else if (pro->proposedCharSets[i]->which ==
359 (*charsets)[i] = set_form(
361 }
362 }
363 else
364 *num_charsets = 0;
365 }
366
367 if (langs && num_langs)
368 {
369 if (pro->num_proposedlanguages)
370 {
371 *num_langs = pro->num_proposedlanguages;
372
373 (*langs) = (char **)
374 nmem_malloc(mem, pro->num_proposedlanguages * sizeof(char *));
375
376 for (i = 0; i < pro->num_proposedlanguages; i++)
377 (*langs)[i] = nmem_strdup(mem, pro->proposedlanguages[i]);
378 }
379 else
380 *num_langs = 0;
381 }
382
383 if (pro->recordsInSelectedCharSets && selected)
384 *selected = *pro->recordsInSelectedCharSets;
385}
386
387/* Return charset, lang, selected from negotiation.. Client side */
389 char **charset, char **lang, int *selected)
390{
391 Z_TargetResponse *res = p->u.response;
392
393 if (charset && res->which == Z_TargetResponse_private &&
395 {
397
398 if (pext->which == Z_External_octet)
399 {
400 *charset = (char *)
401 nmem_malloc(mem, (1+pext->u.octet_aligned->len)*sizeof(char));
402 memcpy(*charset, pext->u.octet_aligned->buf,
403 pext->u.octet_aligned->len);
404 (*charset)[pext->u.octet_aligned->len] = 0;
405 }
406 }
407 if (charset && res->which == Z_TargetResponse_iso10646)
408 *charset = set_form(res->u.iso10646->encodingLevel);
409 if (lang && res->selectedLanguage)
410 *lang = nmem_strdup(mem, res->selectedLanguage);
411
412 if (selected && res->recordsInSelectedCharSets)
413 *selected = *res->recordsInSelectedCharSets;
414}
415/*
416 * Local variables:
417 * c-basic-offset: 4
418 * c-file-style: "Stroustrup"
419 * indent-tabs-mode: nil
420 * End:
421 * vim: shiftwidth=4 tabstop=8 expandtab
422 */
423
static int get_form(const char *charset)
Definition charneg.c:39
static Z_External * z_ext_record2(ODR o, const char *buf)
Definition charneg.c:23
Z_External * yaz_set_proposal_charneg(ODR o, const char **charsets, int num_charsets, const char **langs, int num_langs, int selected)
Definition charneg.c:153
static Z_TargetResponse * z_get_TargetResponse(ODR o, const char *charset, const char *lang, int selected)
Definition charneg.c:202
static Z_CharSetandLanguageNegotiation * z_get_CharSetandLanguageNegotiation(ODR o)
Definition charneg.c:141
static Z_OriginProposal_0 * z_get_OriginProposal_0(ODR o, const char *charset)
Definition charneg.c:71
static char * set_form(Odr_oid *encoding)
Definition charneg.c:55
Z_External * yaz_set_proposal_charneg_list(ODR o, const char *delim, const char *charset_list, const char *lang_list, int selected)
Definition charneg.c:175
void yaz_get_proposal_charneg(NMEM mem, Z_CharSetandLanguageNegotiation *p, char ***charsets, int *num_charsets, char ***langs, int *num_langs, int *selected)
Definition charneg.c:318
Z_External * yaz_set_response_charneg(ODR o, const char *charset, const char *lang, int selected)
Definition charneg.c:242
void yaz_get_response_charneg(NMEM mem, Z_CharSetandLanguageNegotiation *p, char **charset, char **lang, int *selected)
Definition charneg.c:388
static Z_OriginProposal * z_get_OriginProposal(ODR o, const char **charsets, int num_charsets, const char **langs, int num_langs, int selected)
Definition charneg.c:106
Z_CharSetandLanguageNegotiation * yaz_get_charneg_record(Z_OtherInformation *p)
Definition charneg.c:261
int yaz_del_charneg_record(Z_OtherInformation **p)
Definition charneg.c:285
Header for Z39.50 Charset negotiation utilities.
int yaz_matchstr(const char *s1, const char *s2)
match strings - independent of case and '-'
Definition matchstr.c:42
void * nmem_malloc(NMEM n, size_t size)
allocates memory block on NMEM handle
Definition nmem.c:145
struct nmem_control * NMEM
NMEM handle (an opaque pointer to memory).
Definition nmem.h:44
void nmem_strsplit(NMEM nmem, const char *delim, const char *dstr, char ***darray, int *num)
allocates sub strings out of string using certain delimitors
Definition nmemsdup.c:62
char * nmem_strdup(NMEM mem, const char *src)
allocates string on NMEM handle (similar strdup)
Definition nmemsdup.c:19
#define odr_getmem(o)
Definition odr.h:216
#define bool_t
Definition odr.h:52
struct odr * ODR
Definition odr.h:121
Odr_oct * odr_create_Odr_oct(ODR o, const char *buf, int sz)
Definition odr_mem.c:66
void * odr_malloc(ODR o, size_t size)
Definition odr_mem.c:31
char * odr_strdup(ODR o, const char *str)
Definition odr_mem.c:36
Odr_oid * odr_oiddup(ODR odr, const Odr_oid *o)
Definition odr_util.c:60
Odr_oid * odr_getoidbystr(ODR o, const char *str)
Definition odr_util.c:77
Header for OID database.
const Odr_oid yaz_oid_negot_charset_3[]
Definition oid_std.c:140
const Odr_oid yaz_oid_negot_charset_id[]
Definition oid_std.c:142
int oid_oidcmp(const Odr_oid *o1, const Odr_oid *o2)
compares OIDs
Definition oid_util.c:34
int oid_oidlen(const Odr_oid *o)
returns length of OIDs
Definition oid_util.c:49
short Odr_oid
Definition oid_util.h:42
Header for Z39.50 OtherInfo utilities.
#define Z_External_octet
Definition prt-ext.h:66
#define Z_External_charSetandLanguageNegotiation
Definition prt-ext.h:88
void yaz_snprintf(char *buf, size_t size, const char *fmt,...)
Definition snprintf.c:31
Header for config file reading utilities.
Z_TargetResponse * response
Definition z-charneg.h:64
Z_OriginProposal * proposal
Definition z-charneg.h:63
union Z_CharSetandLanguageNegotiation::@127242022024235010345232225261367222210142073064 u
structure for all known EXTERNALs
Definition prt-ext.h:59
Z_CharSetandLanguageNegotiation * charNeg3
Definition prt-ext.h:132
Odr_int * indirect_reference
Definition prt-ext.h:61
union Z_External::@173112132151266201036013025012152147264102163302 u
int which
Definition prt-ext.h:63
Odr_oid * direct_reference
Definition prt-ext.h:60
Odr_oct * octet_aligned
Definition prt-ext.h:105
char * descriptor
Definition prt-ext.h:62
Odr_oid * encodingLevel
Definition z-charneg.h:183
Odr_oid * collections
Definition z-charneg.h:182
Z_PrivateCharacterSet * zprivate
Definition z-charneg.h:75
union Z_OriginProposal_0::@350047213161110340275037164040022047055335047144 u
Z_Iso10646 * iso10646
Definition z-charneg.h:74
Z_LanguageCode ** proposedlanguages
Definition z-charneg.h:86
int num_proposedlanguages
Definition z-charneg.h:85
Z_OriginProposal_0 ** proposedCharSets
Definition z-charneg.h:84
int num_proposedCharSets
Definition z-charneg.h:83
Odr_bool * recordsInSelectedCharSets
Definition z-charneg.h:87
Z_External * externallyDefinedInfo
Definition z-core.h:1285
union Z_OtherInformationUnit::@203311166000256233060143271176054366177037254136 information
Z_OtherInformationUnit ** list
Definition z-core.h:1296
Z_External * externallySpecified
Definition z-charneg.h:115
union Z_PrivateCharacterSet::@234061056346327217307337211221361230325257104130 u
Z_PrivateCharacterSet * zprivate
Definition z-charneg.h:95
Odr_bool * recordsInSelectedCharSets
Definition z-charneg.h:103
union Z_TargetResponse::@071030250150156075157174046113117140236075113034 u
Z_Iso10646 * iso10646
Definition z-charneg.h:94
Z_LanguageCode * selectedLanguage
Definition z-charneg.h:102
int len
Definition odr.h:102
char * buf
Definition odr.h:101
Header for common YAZ utilities.
ASN.1 Module NegotiationRecordDefinition-charSetandLanguageNegotiation-3.
#define Z_CharSetandLanguageNegotiation_proposal
Definition z-charneg.h:65
#define Z_OriginProposal_0_private
Definition z-charneg.h:78
#define Z_PrivateCharacterSet_externallySpecified
Definition z-charneg.h:118
#define Z_CharSetandLanguageNegotiation_response
Definition z-charneg.h:66
#define Z_OriginProposal_0_iso10646
Definition z-charneg.h:77
#define Z_TargetResponse_private
Definition z-charneg.h:99
#define Z_TargetResponse_iso10646
Definition z-charneg.h:98
#define Z_OtherInfo_externallyDefinedInfo
Definition z-core.h:1289