0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038 #ifndef _GNU_SOURCE
0039 #define _GNU_SOURCE
0040 #endif
0041 #include <stdio.h>
0042
0043 #include <string.h>
0044
0045 #include <stdlib.h>
0046 #include <memory.h>
0047 #include <errno.h>
0048
0049 #include <ubf.h>
0050 #include <ubf_int.h> /* Internal headers for UBF... */
0051 #include <fdatatype.h>
0052 #include <ferror.h>
0053 #include <fieldtable.h>
0054 #include <ndrstandard.h>
0055 #include <ndebug.h>
0056 #include <cf.h>
0057 #include <utils.h>
0058 #include <ubf_tls.h>
0059 #include <ubfview.h>
0060
0061 #include "atmi_int.h"
0062
0063
0064
0065 #define OUTPUT_FORMAT_WDATA fmt_wdata, ndrx_Bfname_int(bfldid), p
0066 #define OUTPUT_FORMAT_NDATA fmt_ndata, ndrx_Bfname_int(bfldid)
0067
0068
0069
0070
0071
0072
0073
0074
0075
0076
0077
0078
0079
0080
0081
0082
0083
0084
0085
0086
0087
0088
0089 expublic int ndrx_Bfprint (UBFH *p_ub, FILE * outf,
0090 ndrx_plugin_tplogprintubf_hook_t p_writef, void *dataptr1, int level)
0091 {
0092 int ret=EXSUCCEED;
0093 BFLDID bfldid;
0094 BFLDLEN len;
0095 BFLDOCC occ;
0096 char *p;
0097 int fldtype;
0098 char *cnv_buf = NULL;
0099 char *tmp_buf = NULL;
0100 BFLDLEN cnv_len;
0101 char fmt_wdata[256];
0102 char fmt_ndata[256];
0103 int i;
0104 BVIEWFLD *vdata;
0105 Bnext_state_t bprint_state;
0106 int temp_len;
0107
0108 UBF_TLS_ENTRY;
0109
0110 UBF_LOG(log_debug, "%s enter at level %d", __func__, level);
0111
0112 memset(&bprint_state, 0, sizeof(bprint_state));
0113
0114 for (i=0; i<level; i++)
0115 {
0116 fmt_wdata[i]='\t';
0117 fmt_ndata[i]='\t';
0118 }
0119
0120 fmt_wdata[i]=EXEOS;
0121 fmt_ndata[i]=EXEOS;
0122
0123 NDRX_STRCAT_S(fmt_wdata, sizeof(fmt_wdata), "%s\t%s\n");
0124 NDRX_STRCAT_S(fmt_ndata, sizeof(fmt_ndata), "%s\t\n");
0125
0126 UBF_LOG(log_debug, "fmt_wdata=[%s] fmt_ndata=[%s]", fmt_wdata, fmt_ndata);
0127
0128 bfldid = BFIRSTFLDID;
0129
0130 while(1==ndrx_Bnext(&bprint_state,
0131 p_ub, &bfldid, &occ, NULL, &len, &p))
0132 {
0133 if (NULL!=tmp_buf)
0134 {
0135 NDRX_FREE(tmp_buf);
0136 tmp_buf = NULL;
0137 }
0138
0139 if (NULL!=cnv_buf)
0140 {
0141 NDRX_FREE(cnv_buf);
0142 cnv_buf = NULL;
0143 }
0144
0145 fldtype=bfldid>>EFFECTIVE_BITS;
0146
0147
0148 if (BFLD_VIEW==fldtype)
0149 {
0150 vdata = (BVIEWFLD *)p;
0151
0152 p=vdata->vname;
0153 len=strlen(vdata->vname)+1;
0154 }
0155 else if (BFLD_UBF==fldtype)
0156 {
0157
0158 len = 0;
0159 }
0160 else if (BFLD_STRING!=fldtype && BFLD_CARRAY!=fldtype)
0161 {
0162 cnv_buf=ndrx_Btypcvt(&cnv_len, BFLD_STRING, p, fldtype, len);
0163
0164 if (NULL==cnv_buf)
0165 {
0166
0167
0168 break;
0169 }
0170 else
0171 {
0172 p=cnv_buf;
0173 }
0174
0175
0176 if (BFLD_CHAR==fldtype &&
0177 (temp_len = ndrx_get_nonprintable_char_tmpspace(p, cnv_len)) &&
0178 temp_len!=cnv_len)
0179 {
0180 UBF_LOG(log_debug, "Containing special characters -"
0181 " needs to temp buffer for prefixing");
0182 tmp_buf=NDRX_MALLOC(temp_len+1);
0183 if (NULL==tmp_buf)
0184 {
0185 ndrx_Bset_error_fmt(BMALLOC, "%s: Failed to allocate ",
0186 __func__, temp_len+1);
0187 EXFAIL_OUT(ret);
0188 }
0189
0190
0191 ndrx_build_printable_string(tmp_buf, temp_len+1, p, len);
0192 p = tmp_buf;
0193 }
0194
0195 len=cnv_len;
0196 }
0197
0198 else if (BFLD_STRING==fldtype || BFLD_CARRAY==fldtype)
0199 {
0200
0201 if (BFLD_STRING==fldtype)
0202 {
0203 len--;
0204 }
0205
0206 temp_len = ndrx_get_nonprintable_char_tmpspace(p, len);
0207
0208 if (temp_len!=len)
0209 {
0210 UBF_LOG(log_debug, "Containing special characters -"
0211 " needs to temp buffer for prefixing");
0212 tmp_buf=NDRX_MALLOC(temp_len+1);
0213 if (NULL==tmp_buf)
0214 {
0215 ndrx_Bset_error_fmt(BMALLOC, "%s: Failed to allocate ",
0216 __func__, temp_len+1);
0217 EXFAIL_OUT(ret);
0218 }
0219
0220
0221 ndrx_build_printable_string(tmp_buf, temp_len+1, p, len);
0222 p = tmp_buf;
0223 }
0224 else if (BFLD_CARRAY==fldtype)
0225 {
0226 tmp_buf=NDRX_MALLOC(temp_len+1);
0227
0228 memcpy(tmp_buf, p, temp_len);
0229
0230 if (NULL==tmp_buf)
0231 {
0232 ndrx_Bset_error_fmt(BMALLOC, "%s: Failed to allocate ",
0233 __func__, temp_len+1);
0234 EXFAIL_OUT(ret);
0235 }
0236 tmp_buf[temp_len] = EXEOS;
0237 p = tmp_buf;
0238 }
0239 }
0240
0241
0242 if (len>0)
0243 {
0244
0245
0246 if (NULL!=p_writef)
0247 {
0248 char *tmp;
0249 long tmp_len;
0250 int do_write = EXFALSE;
0251
0252 NDRX_ASPRINTF(&tmp, &tmp_len, OUTPUT_FORMAT_WDATA);
0253
0254 if (NULL==tmp)
0255 {
0256 ndrx_Bset_error_fmt(BMALLOC, "%s: NDRX_ASPRINTF failed",
0257 __func__);
0258 EXFAIL_OUT(ret);
0259 }
0260
0261 tmp_len++;
0262
0263 if (EXSUCCEED!=(ret=p_writef(&tmp, tmp_len, dataptr1, &do_write,
0264 outf, bfldid)))
0265 {
0266 ndrx_Bset_error_fmt(BEINVAL, "%s: p_writef user function "
0267 "failed with %d for [%s]",
0268 __func__, ret, tmp);
0269 NDRX_FREE(tmp);
0270 EXFAIL_OUT(ret);
0271 }
0272
0273 if (do_write)
0274 {
0275 fprintf(outf, "%s", tmp);
0276 }
0277
0278 NDRX_FREE(tmp);
0279 }
0280 else
0281 {
0282 fprintf(outf, OUTPUT_FORMAT_WDATA);
0283 }
0284
0285 }
0286 else
0287 {
0288 if (NULL!=p_writef)
0289 {
0290 char *tmp;
0291 long tmp_len;
0292 int do_write = EXFALSE;
0293
0294 NDRX_ASPRINTF(&tmp, &tmp_len, OUTPUT_FORMAT_NDATA);
0295
0296 if (NULL==tmp)
0297 {
0298 ndrx_Bset_error_fmt(BMALLOC, "%s: NDRX_ASPRINTF failed 2",
0299 __func__);
0300 EXFAIL_OUT(ret);
0301 }
0302
0303 tmp_len++;
0304
0305 if (EXSUCCEED!=(ret=p_writef(&tmp, tmp_len, dataptr1, &do_write, outf,
0306 bfldid)))
0307 {
0308 ndrx_Bset_error_fmt(BEINVAL, "%s: p_writef user function "
0309 "failed with %d for [%s] 2",
0310 __func__, ret, tmp);
0311 NDRX_FREE(tmp);
0312 EXFAIL_OUT(ret);
0313 }
0314
0315 if (do_write)
0316 {
0317 fprintf(outf, "%s", tmp);
0318 }
0319
0320 NDRX_FREE(tmp);
0321 }
0322 else
0323 {
0324 fprintf(outf, OUTPUT_FORMAT_NDATA);
0325 }
0326
0327 }
0328
0329 if (NULL!=outf && ferror(outf))
0330 {
0331 ndrx_Bset_error_fmt(BEUNIX, "Failed to write to file with error: [%s]",
0332 strerror(errno));
0333 EXFAIL_OUT(ret);
0334 }
0335
0336
0337 if (BFLD_UBF==fldtype)
0338 {
0339 if (EXSUCCEED!=ndrx_Bfprint ((UBFH *)p, outf, p_writef, dataptr1, level+1))
0340 {
0341 UBF_LOG(log_error, "ndrx_Bfprint failed at level %d", level+1);
0342 EXFAIL_OUT(ret);
0343 }
0344 }
0345
0346 else if (BFLD_VIEW==fldtype && len > 1)
0347 {
0348
0349 if (EXSUCCEED!=ndrx_Bvfprint (vdata->data, vdata->vname, outf,
0350 p_writef, dataptr1, level+1))
0351 {
0352 UBF_LOG(log_error, "ndrx_Bvfprint failed at level %d", level+1);
0353 EXFAIL_OUT(ret);
0354 }
0355 }
0356 }
0357
0358 out:
0359
0360 if (NULL!=tmp_buf)
0361 {
0362 NDRX_FREE(tmp_buf);
0363 }
0364
0365 if (NULL!=cnv_buf)
0366 {
0367 NDRX_FREE(cnv_buf);
0368 }
0369
0370
0371 if (0==level)
0372 {
0373 fflush(outf);
0374 }
0375
0376 return ret;
0377 }
0378
0379
0380
0381
0382
0383
0384
0385
0386
0387
0388
0389
0390
0391
0392
0393
0394
0395
0396
0397
0398 expublic int ndrx_Bextread (UBFH * p_ub, FILE *inf,
0399 long (*p_readf)(char *buffer, long bufsz, void *dataptr1),
0400 void *dataptr1, int level, char **p_readbuf_buffered)
0401 {
0402 int ret=EXSUCCEED;
0403 int line=0;
0404 char *readbuf=NULL;
0405 size_t readbuf_len;
0406 char fldnm[UBFFLDMAX+1];
0407 char view[NDRX_VIEW_NAME_LEN+1];
0408 char *value=NULL;
0409 size_t value_len;
0410 char flag;
0411 char *p;
0412 char *tok;
0413 BFLDID bfldid;
0414 BFLDID bfldid_from;
0415 int fldtype;
0416 int cpylen;
0417 int len;
0418 char *readbuf_buffered=NULL;
0419 int nr_lead_tabs;
0420 int is_eof=EXFALSE;
0421 NDRX_USYSBUF_MALLOC_WERR_OUT(readbuf, readbuf_len, ret);
0422 NDRX_USYSBUF_MALLOC_WERR_OUT(value, value_len, ret);
0423
0424
0425 while(!is_eof)
0426 {
0427
0428 if (NULL!=readbuf_buffered)
0429 {
0430 NDRX_SYSBUF_FREE(readbuf);
0431 readbuf=readbuf_buffered;
0432 readbuf_buffered=NULL;
0433 }
0434 else if (NULL!=p_readf)
0435 {
0436
0437 ret = (int)p_readf(readbuf, readbuf_len, dataptr1);
0438
0439 if (0==ret)
0440 {
0441
0442 break;
0443 }
0444 if (ret < 0)
0445 {
0446 ndrx_Bset_error_fmt(BEUNIX, "p_readf() user callback failed");
0447
0448 EXFAIL_OUT(ret);
0449 }
0450 ret = EXSUCCEED;
0451 }
0452 else
0453 {
0454 if (NULL==fgets(readbuf, readbuf_len, inf))
0455 {
0456
0457
0458
0459
0460 if (!feof(inf))
0461 {
0462
0463 ndrx_Bset_error_fmt(BEUNIX, "Failed to read from file "
0464 "with error: [%s]", strerror(errno));
0465 EXFAIL_OUT(ret);
0466 }
0467
0468 break;
0469 }
0470 }
0471
0472 len = strlen(readbuf);
0473 line++;
0474 bfldid=BBADFLDID;
0475 value[0] = EXEOS;
0476 fldnm[0] = EXEOS;
0477 p = readbuf;
0478
0479 if ('#'==p[0])
0480 {
0481 continue;
0482 }
0483
0484
0485
0486
0487 if (0==strcmp(p, "\n"))
0488 {
0489 continue;
0490 }
0491
0492
0493 nr_lead_tabs=0;
0494 while (*p=='\t')
0495 {
0496 nr_lead_tabs++;
0497 p++;
0498 }
0499
0500
0501 if (nr_lead_tabs < level)
0502 {
0503 UBF_LOG(log_debug, "Found tab level %d current %d, popping up line %d",
0504 nr_lead_tabs, level, line);
0505 if (NULL!=p_readbuf_buffered)
0506 {
0507
0508 *p_readbuf_buffered=readbuf;
0509 readbuf=NULL;
0510 }
0511
0512 goto out;
0513 }
0514 else if (nr_lead_tabs > level)
0515 {
0516 ndrx_Bset_error_fmt(BSYNTAX, "Tab level %d expected %d or less - "
0517 "invalid data at line %d", nr_lead_tabs, level, line);
0518 EXFAIL_OUT(ret);
0519 }
0520
0521
0522 flag = 0;
0523
0524 if ('-'==p[0] || '+'==p[0] || '='==p[0])
0525 {
0526
0527
0528 flag=p[0];
0529
0530 if (' '!=p[1])
0531 {
0532 ndrx_Bset_error_fmt(BSYNTAX, "Space does not follow the flag on "
0533 "line %d!", line);
0534
0535 EXFAIL_OUT(ret);
0536 }
0537 else
0538 {
0539
0540 p+=2;
0541 }
0542 }
0543
0544 tok = strchr(p, '\t');
0545 if (NULL==tok)
0546 {
0547 ndrx_Bset_error_fmt(BSYNTAX, "No tab on "
0548 "line %d!", line);
0549 EXFAIL_OUT(ret);
0550 }
0551 else if (tok==readbuf)
0552 {
0553 ndrx_Bset_error_fmt(BSYNTAX, "Line should not start with tab on "
0554 "line %d!", line);
0555 EXFAIL_OUT(ret);
0556 }
0557 else
0558 {
0559 int tmpl = strlen(p);
0560
0561
0562 if (p[tmpl-1]!='\n')
0563 {
0564
0565 if (NULL==p_readf)
0566 {
0567 ndrx_Bset_error_fmt(BSYNTAX, "Line %d does not "
0568 "terminate with newline!", line);
0569 EXFAIL_OUT(ret);
0570 }
0571 }
0572 else
0573 {
0574 p[tmpl-1]=EXEOS;
0575 }
0576 }
0577
0578
0579 cpylen = (tok-p);
0580
0581 NDRX_STRNCPY_EOS(fldnm, p, cpylen, sizeof(fldnm));
0582
0583
0584 NDRX_STRCPY_SAFE_DST(value, tok+1, value_len);
0585 UBF_LOG(log_debug, "Got [%s]:[%s]", fldnm, value);
0586
0587
0588
0589
0590 bfldid = ndrx_Bfldid_int(fldnm);
0591 if (BBADFLDID==bfldid)
0592 {
0593 ndrx_Bset_error_fmt(BBADNAME, "Cannot resolve field ID from [%s] on"
0594 "line %d!", fldnm, line);
0595 EXFAIL_OUT(ret);
0596 }
0597
0598
0599 fldtype=bfldid >> EFFECTIVE_BITS;
0600
0601
0602 if (IS_TYPE_INVALID(fldtype))
0603 {
0604 ndrx_Bset_error_fmt(BBADFLD, "BAD field's type [%d] on"
0605 "line %d!", fldtype, line);
0606 EXFAIL_OUT(ret);
0607 }
0608
0609
0610 if (BFLD_PTR==fldtype && !(ndrx_G_apiflags & NDRX_APIFLAGS_UBFPTRPARSE))
0611 {
0612 flag='N';
0613 }
0614 else if ((BFLD_STRING == fldtype ||
0615 BFLD_CARRAY == fldtype || BFLD_CHAR == fldtype) && '='!=flag)
0616 {
0617 if (EXFAIL==ndrx_normalize_string(value, &len))
0618 {
0619 ndrx_Bset_error_fmt(BSYNTAX, "Cannot normalize value on line %d",
0620 line);
0621 EXFAIL_OUT(ret);
0622 }
0623 }
0624 else if (BFLD_UBF == fldtype && '='!=flag)
0625 {
0626
0627 if (EXSUCCEED!=Binit((UBFH*)value, value_len))
0628 {
0629 UBF_LOG(log_error, "Failed to init %p/%z level: %d",
0630 value, value_len, level);
0631 EXFAIL_OUT(ret);
0632 }
0633
0634
0635 if (EXSUCCEED!=ndrx_Bextread ((UBFH*)value, inf,
0636 p_readf, dataptr1, level+1, &readbuf_buffered))
0637 {
0638 UBF_LOG(log_error, "Failed to parse inner UBF level %d", level+1);
0639 EXFAIL_OUT(ret);
0640 }
0641
0642
0643 if (NULL==readbuf_buffered)
0644 {
0645 is_eof=EXTRUE;
0646 }
0647 }
0648 else if (BFLD_VIEW == fldtype && '='!=flag)
0649 {
0650
0651
0652
0653
0654 ndrx_typedview_t *v = NULL;
0655
0656 NDRX_STRCPY_SAFE(view, value);
0657
0658 if (EXSUCCEED!=ndrx_view_init())
0659 {
0660 UBF_LOG(log_error, "Failed to init view sub-system");
0661 EXFAIL_OUT(ret);
0662 }
0663
0664
0665 if (EXEOS!=view[0])
0666 {
0667 if (NULL==(v = ndrx_view_get_view(view)))
0668 {
0669 ndrx_Bset_error_fmt(BBADVIEW, "View [%s] not found!", view);
0670 EXFAIL_OUT(ret);
0671 }
0672
0673 if (value_len<v->ssize)
0674 {
0675 ndrx_Bset_error_fmt(BNOSPACE, "Temporary buffer size %zu "
0676 "is shorter than view size %ld", value_len, v->ssize);
0677 EXFAIL_OUT(ret);
0678 }
0679
0680
0681 if (EXSUCCEED!=ndrx_Bvextread (value, view, inf, p_readf, dataptr1,
0682 level+1, &readbuf_buffered))
0683 {
0684 UBF_LOG(log_error, "Failed to parse view [%s] at level %d",
0685 view, level+1);
0686 EXFAIL_OUT(ret);
0687 }
0688 }
0689
0690
0691 }
0692
0693
0694 if (0==flag)
0695 {
0696 if (BFLD_UBF == fldtype)
0697 {
0698 if (EXSUCCEED!=(ret=Badd(p_ub, bfldid, value, 0)))
0699 {
0700 EXFAIL_OUT(ret);
0701 }
0702 }
0703 else if (BFLD_VIEW == fldtype)
0704 {
0705 BVIEWFLD vadd;
0706
0707 vadd.data=value;
0708 NDRX_STRCPY_SAFE(vadd.vname, view);
0709 vadd.vflags=0;
0710 if (EXSUCCEED!=(ret=Badd(p_ub, bfldid, (char *)&vadd, 0)))
0711 {
0712 EXFAIL_OUT(ret);
0713 }
0714 }
0715 else if (EXSUCCEED!=(ret=CBadd(p_ub, bfldid, value, len, BFLD_CARRAY)))
0716 {
0717 EXFAIL_OUT(ret);
0718 }
0719 }
0720 else if ('+'==flag)
0721 {
0722 if (BFLD_UBF == fldtype)
0723 {
0724 if (EXSUCCEED!=(ret=Bchg(p_ub, bfldid, 0, value, 0)))
0725 {
0726 EXFAIL_OUT(ret);
0727 }
0728 }
0729 else if (BFLD_VIEW == fldtype)
0730 {
0731 BVIEWFLD vadd;
0732
0733 vadd.data=value;
0734 NDRX_STRCPY_SAFE(vadd.vname, view);
0735 vadd.vflags=0;
0736 if (EXSUCCEED!=(ret=Bchg(p_ub, bfldid, 0, (char *)&vadd, 0)))
0737 {
0738 EXFAIL_OUT(ret);
0739 }
0740 }
0741 else if (EXSUCCEED!=(ret=CBchg(p_ub, bfldid, 0, value, len, BFLD_CARRAY)))
0742 {
0743 EXFAIL_OUT(ret);
0744 }
0745 }
0746 else if ('-'==flag)
0747 {
0748 if (EXSUCCEED!=(ret=Bdel(p_ub, bfldid, 0)))
0749 {
0750 EXFAIL_OUT(ret);
0751 }
0752 }
0753 else if ('='==flag)
0754 {
0755
0756 bfldid_from = ndrx_Bfldid_int(value);
0757 if (BBADFLDID==bfldid_from)
0758 {
0759 ndrx_Bset_error_fmt(BBADNAME, "Cannot resolve field ID from [%s] on"
0760 "line %d!", value, line);
0761 EXFAIL_OUT(ret);
0762 }
0763 else
0764 {
0765 BFLDLEN len_from=0;
0766
0767 char *copy_form = Bgetalloc (p_ub, bfldid_from, 0, &len_from);
0768
0769
0770 if (NULL!=copy_form)
0771 {
0772
0773
0774
0775
0776
0777
0778
0779
0780 if (Bfldtype(bfldid_from) == fldtype)
0781 {
0782 if (EXSUCCEED!=(ret=Bchg(p_ub, bfldid, 0, copy_form, len_from)))
0783 {
0784 NDRX_FREE(copy_form);
0785 EXFAIL_OUT(ret);
0786 }
0787 }
0788 else if (EXSUCCEED!=(ret=CBchg(p_ub, bfldid, 0, copy_form,
0789 len_from, Bfldtype(bfldid_from))))
0790 {
0791 NDRX_FREE(copy_form);
0792 EXFAIL_OUT(ret);
0793 }
0794
0795 NDRX_FREE(copy_form);
0796 }
0797 else
0798 {
0799 EXFAIL_OUT(ret);
0800 }
0801 }
0802 }
0803 else if ('N'==flag)
0804 {
0805 UBF_LOG(log_error, "Ignoring field %d", bfldid);
0806 }
0807 }
0808
0809 out:
0810
0811 if (NULL!=readbuf_buffered)
0812 {
0813 NDRX_SYSBUF_FREE(readbuf_buffered);
0814 }
0815
0816 if (NULL!=readbuf)
0817 {
0818 NDRX_SYSBUF_FREE(readbuf);
0819 }
0820
0821 if (NULL!=value)
0822 {
0823 NDRX_SYSBUF_FREE(value);
0824 }
0825
0826 UBF_LOG(log_debug, "%s: return %d", __func__, ret);
0827
0828 return ret;
0829 }
0830
0831