ReactOS  0.4.14-dev-815-ge410a12
buf.c
Go to the documentation of this file.
1 /*
2  * buf.c: memory buffers for libxml2
3  *
4  * new buffer structures and entry points to simplify the maintainance
5  * of libxml2 and ensure we keep good control over memory allocations
6  * and stay 64 bits clean.
7  * The new entry point use the xmlBufPtr opaque structure and
8  * xmlBuf...() counterparts to the old xmlBuf...() functions
9  *
10  * See Copyright for the status of this software.
11  *
12  * daniel@veillard.com
13  */
14 
15 #define IN_LIBXML
16 #include "libxml.h"
17 
18 #include <string.h> /* for memset() only ! */
19 #include <limits.h>
20 #ifdef HAVE_CTYPE_H
21 #include <ctype.h>
22 #endif
23 #ifdef HAVE_STDLIB_H
24 #include <stdlib.h>
25 #endif
26 
27 #include <libxml/tree.h>
28 #include <libxml/globals.h>
29 #include <libxml/tree.h>
30 #include <libxml/parserInternals.h> /* for XML_MAX_TEXT_LENGTH */
31 #include "buf.h"
32 
33 #define WITH_BUFFER_COMPAT
34 
43 struct _xmlBuf {
44  xmlChar *content; /* The buffer content UTF8 */
45  unsigned int compat_use; /* for binary compatibility */
46  unsigned int compat_size; /* for binary compatibility */
47  xmlBufferAllocationScheme alloc; /* The realloc method */
48  xmlChar *contentIO; /* in IO mode we may have a different base */
49  size_t use; /* The buffer size used */
50  size_t size; /* The buffer size */
51  xmlBufferPtr buffer; /* wrapper for an old buffer */
52  int error; /* an error code if a failure occurred */
53 };
54 
55 #ifdef WITH_BUFFER_COMPAT
56 /*
57  * Macro for compatibility with xmlBuffer to be used after an xmlBuf
58  * is updated. This makes sure the compat fields are updated too.
59  */
60 #define UPDATE_COMPAT(buf) \
61  if (buf->size < INT_MAX) buf->compat_size = buf->size; \
62  else buf->compat_size = INT_MAX; \
63  if (buf->use < INT_MAX) buf->compat_use = buf->use; \
64  else buf->compat_use = INT_MAX;
65 
66 /*
67  * Macro for compatibility with xmlBuffer to be used in all the xmlBuf
68  * entry points, it checks that the compat fields have not been modified
69  * by direct call to xmlBuffer function from code compiled before 2.9.0 .
70  */
71 #define CHECK_COMPAT(buf) \
72  if (buf->size != (size_t) buf->compat_size) \
73  if (buf->compat_size < INT_MAX) \
74  buf->size = buf->compat_size; \
75  if (buf->use != (size_t) buf->compat_use) \
76  if (buf->compat_use < INT_MAX) \
77  buf->use = buf->compat_use;
78 
79 #else /* ! WITH_BUFFER_COMPAT */
80 #define UPDATE_COMPAT(buf)
81 #define CHECK_COMPAT(buf)
82 #endif /* WITH_BUFFER_COMPAT */
83 
91 static void
93 {
94  __xmlSimpleError(XML_FROM_BUFFER, XML_ERR_NO_MEMORY, NULL, NULL, extra);
95  if ((buf) && (buf->error == 0))
96  buf->error = XML_ERR_NO_MEMORY;
97 }
98 
106 static void
108 {
109  __xmlSimpleError(XML_FROM_BUFFER, XML_BUF_OVERFLOW, NULL, NULL, extra);
110  if ((buf) && (buf->error == 0))
111  buf->error = XML_BUF_OVERFLOW;
112 }
113 
114 
121 xmlBufPtr
123  xmlBufPtr ret;
124 
125  ret = (xmlBufPtr) xmlMalloc(sizeof(xmlBuf));
126  if (ret == NULL) {
127  xmlBufMemoryError(NULL, "creating buffer");
128  return(NULL);
129  }
130  ret->compat_use = 0;
131  ret->use = 0;
132  ret->error = 0;
133  ret->buffer = NULL;
134  ret->size = xmlDefaultBufferSize;
135  ret->compat_size = xmlDefaultBufferSize;
136  ret->alloc = xmlBufferAllocScheme;
137  ret->content = (xmlChar *) xmlMallocAtomic(ret->size * sizeof(xmlChar));
138  if (ret->content == NULL) {
139  xmlBufMemoryError(ret, "creating buffer");
140  xmlFree(ret);
141  return(NULL);
142  }
143  ret->content[0] = 0;
144  ret->contentIO = NULL;
145  return(ret);
146 }
147 
155 xmlBufPtr
157  xmlBufPtr ret;
158 
159  ret = (xmlBufPtr) xmlMalloc(sizeof(xmlBuf));
160  if (ret == NULL) {
161  xmlBufMemoryError(NULL, "creating buffer");
162  return(NULL);
163  }
164  ret->compat_use = 0;
165  ret->use = 0;
166  ret->error = 0;
167  ret->buffer = NULL;
168  ret->alloc = xmlBufferAllocScheme;
169  ret->size = (size ? size+2 : 0); /* +1 for ending null */
170  ret->compat_size = (int) ret->size;
171  if (ret->size){
172  ret->content = (xmlChar *) xmlMallocAtomic(ret->size * sizeof(xmlChar));
173  if (ret->content == NULL) {
174  xmlBufMemoryError(ret, "creating buffer");
175  xmlFree(ret);
176  return(NULL);
177  }
178  ret->content[0] = 0;
179  } else
180  ret->content = NULL;
181  ret->contentIO = NULL;
182  return(ret);
183 }
184 
195 xmlChar *
197  xmlChar *ret;
198 
199  if (buf == NULL)
200  return(NULL);
201  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE)
202  return(NULL);
203  if (buf->buffer != NULL)
204  return(NULL);
205  if (buf->error)
206  return(NULL);
207 
208  ret = buf->content;
209  buf->content = NULL;
210  buf->size = 0;
211  buf->use = 0;
212  buf->compat_use = 0;
213  buf->compat_size = 0;
214 
215  return ret;
216 }
217 
218 
230 xmlBufPtr
231 xmlBufCreateStatic(void *mem, size_t size) {
232  xmlBufPtr ret;
233 
234  if (mem == NULL)
235  return(NULL);
236 
237  ret = (xmlBufPtr) xmlMalloc(sizeof(xmlBuf));
238  if (ret == NULL) {
239  xmlBufMemoryError(NULL, "creating buffer");
240  return(NULL);
241  }
242  if (size < INT_MAX) {
243  ret->compat_use = size;
244  ret->compat_size = size;
245  } else {
246  ret->compat_use = INT_MAX;
247  ret->compat_size = INT_MAX;
248  }
249  ret->use = size;
250  ret->size = size;
252  ret->content = (xmlChar *) mem;
253  ret->error = 0;
254  ret->buffer = NULL;
255  return(ret);
256 }
257 
266 int
268  if (buf == NULL) {
269 #ifdef DEBUG_BUFFER
271  "xmlBufGetAllocationScheme: buf == NULL\n");
272 #endif
273  return(-1);
274  }
275  return(buf->alloc);
276 }
277 
287 int
290  if ((buf == NULL) || (buf->error != 0)) {
291 #ifdef DEBUG_BUFFER
293  "xmlBufSetAllocationScheme: buf == NULL or in error\n");
294 #endif
295  return(-1);
296  }
297  if ((buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) ||
298  (buf->alloc == XML_BUFFER_ALLOC_IO))
299  return(-1);
305  buf->alloc = scheme;
306  if (buf->buffer)
307  buf->buffer->alloc = scheme;
308  return(0);
309  }
310  /*
311  * Switching a buffer ALLOC_IO has the side effect of initializing
312  * the contentIO field with the current content
313  */
314  if (scheme == XML_BUFFER_ALLOC_IO) {
315  buf->alloc = XML_BUFFER_ALLOC_IO;
316  buf->contentIO = buf->content;
317  }
318  return(-1);
319 }
320 
328 void
330  if (buf == NULL) {
331 #ifdef DEBUG_BUFFER
333  "xmlBufFree: buf == NULL\n");
334 #endif
335  return;
336  }
337 
338  if ((buf->alloc == XML_BUFFER_ALLOC_IO) &&
339  (buf->contentIO != NULL)) {
340  xmlFree(buf->contentIO);
341  } else if ((buf->content != NULL) &&
342  (buf->alloc != XML_BUFFER_ALLOC_IMMUTABLE)) {
343  xmlFree(buf->content);
344  }
345  xmlFree(buf);
346 }
347 
354 void
356  if ((buf == NULL) || (buf->error != 0)) return;
357  if (buf->content == NULL) return;
359  buf->use = 0;
360  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) {
361  buf->content = BAD_CAST "";
362  } else if ((buf->alloc == XML_BUFFER_ALLOC_IO) &&
363  (buf->contentIO != NULL)) {
364  size_t start_buf = buf->content - buf->contentIO;
365 
366  buf->size += start_buf;
367  buf->content = buf->contentIO;
368  buf->content[0] = 0;
369  } else {
370  buf->content[0] = 0;
371  }
373 }
374 
387 size_t
389  if ((buf == NULL) || (buf->error != 0)) return(0);
391  if (len == 0) return(0);
392  if (len > buf->use) return(0);
393 
394  buf->use -= len;
395  if ((buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) ||
396  ((buf->alloc == XML_BUFFER_ALLOC_IO) && (buf->contentIO != NULL))) {
397  /*
398  * we just move the content pointer, but also make sure
399  * the perceived buffer size has shrinked accordingly
400  */
401  buf->content += len;
402  buf->size -= len;
403 
404  /*
405  * sometimes though it maybe be better to really shrink
406  * on IO buffers
407  */
408  if ((buf->alloc == XML_BUFFER_ALLOC_IO) && (buf->contentIO != NULL)) {
409  size_t start_buf = buf->content - buf->contentIO;
410  if (start_buf >= buf->size) {
411  memmove(buf->contentIO, &buf->content[0], buf->use);
412  buf->content = buf->contentIO;
413  buf->content[buf->use] = 0;
414  buf->size += start_buf;
415  }
416  }
417  } else {
418  memmove(buf->content, &buf->content[len], buf->use);
419  buf->content[buf->use] = 0;
420  }
422  return(len);
423 }
424 
436 static size_t
438  size_t size;
439  xmlChar *newbuf;
440 
441  if ((buf == NULL) || (buf->error != 0)) return(0);
443 
444  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return(0);
445  if (buf->use + len < buf->size)
446  return(buf->size - buf->use);
447 
448  /*
449  * Windows has a BIG problem on realloc timing, so we try to double
450  * the buffer size (if that's enough) (bug 146697)
451  * Apparently BSD too, and it's probably best for linux too
452  * On an embedded system this may be something to change
453  */
454 #if 1
455  if (buf->size > (size_t) len)
456  size = buf->size * 2;
457  else
458  size = buf->use + len + 100;
459 #else
460  size = buf->use + len + 100;
461 #endif
462 
463  if (buf->alloc == XML_BUFFER_ALLOC_BOUNDED) {
464  /*
465  * Used to provide parsing limits
466  */
467  if ((buf->use + len >= XML_MAX_TEXT_LENGTH) ||
468  (buf->size >= XML_MAX_TEXT_LENGTH)) {
469  xmlBufMemoryError(buf, "buffer error: text too long\n");
470  return(0);
471  }
472  if (size >= XML_MAX_TEXT_LENGTH)
474  }
475  if ((buf->alloc == XML_BUFFER_ALLOC_IO) && (buf->contentIO != NULL)) {
476  size_t start_buf = buf->content - buf->contentIO;
477 
478  newbuf = (xmlChar *) xmlRealloc(buf->contentIO, start_buf + size);
479  if (newbuf == NULL) {
480  xmlBufMemoryError(buf, "growing buffer");
481  return(0);
482  }
483  buf->contentIO = newbuf;
484  buf->content = newbuf + start_buf;
485  } else {
486  newbuf = (xmlChar *) xmlRealloc(buf->content, size);
487  if (newbuf == NULL) {
488  xmlBufMemoryError(buf, "growing buffer");
489  return(0);
490  }
491  buf->content = newbuf;
492  }
493  buf->size = size;
495  return(buf->size - buf->use);
496 }
497 
508 int
510  size_t ret;
511 
512  if ((buf == NULL) || (len < 0)) return(-1);
513  if (len == 0)
514  return(0);
516  if (buf->error != 0)
517  return(-1);
518  return((int) ret);
519 }
520 
530 int
532  if (buf == NULL) return(-1);
533  xmlBufGrowInternal(buf, len + buf->size);
534  if (buf->error)
535  return(-1);
536  return(0);
537 }
538 
547 size_t
549  size_t ret;
550 
551  if ((buf == NULL) || (buf->error != 0)) {
552 #ifdef DEBUG_BUFFER
554  "xmlBufDump: buf == NULL or in error\n");
555 #endif
556  return(0);
557  }
558  if (buf->content == NULL) {
559 #ifdef DEBUG_BUFFER
561  "xmlBufDump: buf->content == NULL\n");
562 #endif
563  return(0);
564  }
566  if (file == NULL)
567  file = stdout;
568  ret = fwrite(buf->content, sizeof(xmlChar), buf->use, file);
569  return(ret);
570 }
571 
581 xmlChar *
583 {
584  if ((!buf) || (buf->error))
585  return NULL;
586 
587  return(buf->content);
588 }
589 
599 xmlChar *
601 {
602  if ((!buf) || (buf->error))
603  return NULL;
605 
606  return(&buf->content[buf->use]);
607 }
608 
620 int
622  if ((buf == NULL) || (buf->error))
623  return(-1);
625  if (len > (buf->size - buf->use))
626  return(-1);
627  buf->use += len;
629  if (buf->size > buf->use)
630  buf->content[buf->use] = 0;
631  else
632  return(-1);
633  return(0);
634 }
635 
645 int
647  if ((buf == NULL) || (buf->error))
648  return(-1);
650  if (len > buf->use)
651  return(-1);
652  buf->use -= len;
653  buf->content[buf->use] = 0;
655  return(0);
656 }
657 
667 size_t
669 {
670  if ((!buf) || (buf->error))
671  return 0;
673 
674  return(buf->use);
675 }
676 
686 size_t
688 {
689  if ((!buf) || (buf->error))
690  return 0;
692 
693  return(buf->use);
694 }
695 
707 size_t
709 {
710  if ((!buf) || (buf->error))
711  return 0;
713 
714  return(buf->size - buf->use);
715 }
716 
725 int
727 {
728  if ((!buf) || (buf->error))
729  return(-1);
731 
732  return(buf->use == 0);
733 }
734 
744 int
746 {
747  unsigned int newSize;
748  xmlChar* rebuf = NULL;
749  size_t start_buf;
750 
751  if ((buf == NULL) || (buf->error))
752  return(0);
754 
755  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return(0);
756  if (buf->alloc == XML_BUFFER_ALLOC_BOUNDED) {
757  /*
758  * Used to provide parsing limits
759  */
760  if (size >= XML_MAX_TEXT_LENGTH) {
761  xmlBufMemoryError(buf, "buffer error: text too long\n");
762  return(0);
763  }
764  }
765 
766  /* Don't resize if we don't have to */
767  if (size < buf->size)
768  return 1;
769 
770  /* figure out new size */
771  switch (buf->alloc){
772  case XML_BUFFER_ALLOC_IO:
774  /*take care of empty case*/
775  newSize = (buf->size ? buf->size*2 : size + 10);
776  while (size > newSize) {
777  if (newSize > UINT_MAX / 2) {
778  xmlBufMemoryError(buf, "growing buffer");
779  return 0;
780  }
781  newSize *= 2;
782  }
783  break;
785  newSize = size+10;
786  break;
788  if (buf->use < BASE_BUFFER_SIZE)
789  newSize = size;
790  else {
791  newSize = buf->size * 2;
792  while (size > newSize) {
793  if (newSize > UINT_MAX / 2) {
794  xmlBufMemoryError(buf, "growing buffer");
795  return 0;
796  }
797  newSize *= 2;
798  }
799  }
800  break;
801 
802  default:
803  newSize = size+10;
804  break;
805  }
806 
807  if ((buf->alloc == XML_BUFFER_ALLOC_IO) && (buf->contentIO != NULL)) {
808  start_buf = buf->content - buf->contentIO;
809 
810  if (start_buf > newSize) {
811  /* move data back to start */
812  memmove(buf->contentIO, buf->content, buf->use);
813  buf->content = buf->contentIO;
814  buf->content[buf->use] = 0;
815  buf->size += start_buf;
816  } else {
817  rebuf = (xmlChar *) xmlRealloc(buf->contentIO, start_buf + newSize);
818  if (rebuf == NULL) {
819  xmlBufMemoryError(buf, "growing buffer");
820  return 0;
821  }
822  buf->contentIO = rebuf;
823  buf->content = rebuf + start_buf;
824  }
825  } else {
826  if (buf->content == NULL) {
827  rebuf = (xmlChar *) xmlMallocAtomic(newSize);
828  } else if (buf->size - buf->use < 100) {
829  rebuf = (xmlChar *) xmlRealloc(buf->content, newSize);
830  } else {
831  /*
832  * if we are reallocating a buffer far from being full, it's
833  * better to make a new allocation and copy only the used range
834  * and free the old one.
835  */
836  rebuf = (xmlChar *) xmlMallocAtomic(newSize);
837  if (rebuf != NULL) {
838  memcpy(rebuf, buf->content, buf->use);
839  xmlFree(buf->content);
840  rebuf[buf->use] = 0;
841  }
842  }
843  if (rebuf == NULL) {
844  xmlBufMemoryError(buf, "growing buffer");
845  return 0;
846  }
847  buf->content = rebuf;
848  }
849  buf->size = newSize;
851 
852  return 1;
853 }
854 
867 int
869  unsigned int needSize;
870 
871  if ((str == NULL) || (buf == NULL) || (buf->error))
872  return -1;
874 
875  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return -1;
876  if (len < -1) {
877 #ifdef DEBUG_BUFFER
879  "xmlBufAdd: len < 0\n");
880 #endif
881  return -1;
882  }
883  if (len == 0) return 0;
884 
885  if (len < 0)
886  len = xmlStrlen(str);
887 
888  if (len < 0) return -1;
889  if (len == 0) return 0;
890 
891  needSize = buf->use + len + 2;
892  if (needSize > buf->size){
893  if (buf->alloc == XML_BUFFER_ALLOC_BOUNDED) {
894  /*
895  * Used to provide parsing limits
896  */
897  if (needSize >= XML_MAX_TEXT_LENGTH) {
898  xmlBufMemoryError(buf, "buffer error: text too long\n");
899  return(-1);
900  }
901  }
902  if (!xmlBufResize(buf, needSize)){
903  xmlBufMemoryError(buf, "growing buffer");
904  return XML_ERR_NO_MEMORY;
905  }
906  }
907 
908  memmove(&buf->content[buf->use], str, len*sizeof(xmlChar));
909  buf->use += len;
910  buf->content[buf->use] = 0;
912  return 0;
913 }
914 
927 int
929  unsigned int needSize;
930 
931  if ((buf == NULL) || (buf->error))
932  return(-1);
934  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return -1;
935  if (str == NULL) {
936 #ifdef DEBUG_BUFFER
938  "xmlBufAddHead: str == NULL\n");
939 #endif
940  return -1;
941  }
942  if (len < -1) {
943 #ifdef DEBUG_BUFFER
945  "xmlBufAddHead: len < 0\n");
946 #endif
947  return -1;
948  }
949  if (len == 0) return 0;
950 
951  if (len < 0)
952  len = xmlStrlen(str);
953 
954  if (len <= 0) return -1;
955 
956  if ((buf->alloc == XML_BUFFER_ALLOC_IO) && (buf->contentIO != NULL)) {
957  size_t start_buf = buf->content - buf->contentIO;
958 
959  if (start_buf > (unsigned int) len) {
960  /*
961  * We can add it in the space previously shrinked
962  */
963  buf->content -= len;
964  memmove(&buf->content[0], str, len);
965  buf->use += len;
966  buf->size += len;
968  return(0);
969  }
970  }
971  needSize = buf->use + len + 2;
972  if (needSize > buf->size){
973  if (buf->alloc == XML_BUFFER_ALLOC_BOUNDED) {
974  /*
975  * Used to provide parsing limits
976  */
977  if (needSize >= XML_MAX_TEXT_LENGTH) {
978  xmlBufMemoryError(buf, "buffer error: text too long\n");
979  return(-1);
980  }
981  }
982  if (!xmlBufResize(buf, needSize)){
983  xmlBufMemoryError(buf, "growing buffer");
984  return XML_ERR_NO_MEMORY;
985  }
986  }
987 
988  memmove(&buf->content[len], &buf->content[0], buf->use);
989  memmove(&buf->content[0], str, len);
990  buf->use += len;
991  buf->content[buf->use] = 0;
993  return 0;
994 }
995 
1006 int
1008  if ((buf == NULL) || (buf->error))
1009  return(-1);
1010  CHECK_COMPAT(buf)
1011  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return -1;
1012  if (str == NULL) return -1;
1013  return xmlBufAdd(buf, str, -1);
1014 }
1015 
1026 int
1027 xmlBufCCat(xmlBufPtr buf, const char *str) {
1028  const char *cur;
1029 
1030  if ((buf == NULL) || (buf->error))
1031  return(-1);
1032  CHECK_COMPAT(buf)
1033  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return -1;
1034  if (str == NULL) {
1035 #ifdef DEBUG_BUFFER
1037  "xmlBufCCat: str == NULL\n");
1038 #endif
1039  return -1;
1040  }
1041  for (cur = str;*cur != 0;cur++) {
1042  if (buf->use + 10 >= buf->size) {
1043  if (!xmlBufResize(buf, buf->use+10)){
1044  xmlBufMemoryError(buf, "growing buffer");
1045  return XML_ERR_NO_MEMORY;
1046  }
1047  }
1048  buf->content[buf->use++] = *cur;
1049  }
1050  buf->content[buf->use] = 0;
1052  return 0;
1053 }
1054 
1066 int
1068  if ((buf == NULL) || (buf->error))
1069  return(-1);
1070  CHECK_COMPAT(buf)
1071  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE)
1072  return(-1);
1073  return(xmlBufCat(buf, string));
1074 }
1075 
1087 int
1088 xmlBufWriteChar(xmlBufPtr buf, const char *string) {
1089  if ((buf == NULL) || (buf->error))
1090  return(-1);
1091  CHECK_COMPAT(buf)
1092  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE)
1093  return(-1);
1094  return(xmlBufCCat(buf, string));
1095 }
1096 
1097 
1110 int
1112  const xmlChar *cur, *base;
1113  if ((buf == NULL) || (buf->error))
1114  return(-1);
1115  CHECK_COMPAT(buf)
1116  if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE)
1117  return(-1);
1118  if (xmlStrchr(string, '\"')) {
1119  if (xmlStrchr(string, '\'')) {
1120 #ifdef DEBUG_BUFFER
1122  "xmlBufWriteQuotedString: string contains quote and double-quotes !\n");
1123 #endif
1124  xmlBufCCat(buf, "\"");
1125  base = cur = string;
1126  while(*cur != 0){
1127  if(*cur == '"'){
1128  if (base != cur)
1129  xmlBufAdd(buf, base, cur - base);
1130  xmlBufAdd(buf, BAD_CAST "&quot;", 6);
1131  cur++;
1132  base = cur;
1133  }
1134  else {
1135  cur++;
1136  }
1137  }
1138  if (base != cur)
1139  xmlBufAdd(buf, base, cur - base);
1140  xmlBufCCat(buf, "\"");
1141  }
1142  else{
1143  xmlBufCCat(buf, "\'");
1144  xmlBufCat(buf, string);
1145  xmlBufCCat(buf, "\'");
1146  }
1147  } else {
1148  xmlBufCCat(buf, "\"");
1149  xmlBufCat(buf, string);
1150  xmlBufCCat(buf, "\"");
1151  }
1152  return(0);
1153 }
1154 
1166 xmlBufPtr
1168  xmlBufPtr ret;
1169 
1170  if (buffer == NULL)
1171  return(NULL);
1172 
1173  ret = (xmlBufPtr) xmlMalloc(sizeof(xmlBuf));
1174  if (ret == NULL) {
1175  xmlBufMemoryError(NULL, "creating buffer");
1176  return(NULL);
1177  }
1178  ret->use = buffer->use;
1179  ret->size = buffer->size;
1180  ret->compat_use = buffer->use;
1181  ret->compat_size = buffer->size;
1182  ret->error = 0;
1183  ret->buffer = buffer;
1184  ret->alloc = buffer->alloc;
1185  ret->content = buffer->content;
1186  ret->contentIO = buffer->contentIO;
1187 
1188  return(ret);
1189 }
1190 
1205  xmlBufferPtr ret;
1206 
1207  if ((buf == NULL) || (buf->error))
1208  return(NULL);
1209  CHECK_COMPAT(buf)
1210  if (buf->buffer == NULL) {
1211  xmlBufFree(buf);
1212  return(NULL);
1213  }
1214 
1215  ret = buf->buffer;
1216  /*
1217  * What to do in case of error in the buffer ???
1218  */
1219  if (buf->use > INT_MAX) {
1220  /*
1221  * Worse case, we really allocated and used more than the
1222  * maximum allowed memory for an xmlBuffer on this architecture.
1223  * Keep the buffer but provide a truncated size value.
1224  */
1225  xmlBufOverflowError(buf, "Used size too big for xmlBuffer");
1226  ret->use = INT_MAX;
1227  ret->size = INT_MAX;
1228  } else if (buf->size > INT_MAX) {
1229  /*
1230  * milder case, we allocated more than the maximum allowed memory
1231  * for an xmlBuffer on this architecture, but used less than the
1232  * limit.
1233  * Keep the buffer but provide a truncated size value.
1234  */
1235  xmlBufOverflowError(buf, "Allocated size too big for xmlBuffer");
1236  ret->size = INT_MAX;
1237  }
1238  ret->use = (int) buf->use;
1239  ret->size = (int) buf->size;
1240  ret->alloc = buf->alloc;
1241  ret->content = buf->content;
1242  ret->contentIO = buf->contentIO;
1243  xmlFree(buf);
1244  return(ret);
1245 }
1246 
1256 int
1258  int ret = 0;
1259 
1260  if ((buf == NULL) || (buf->error)) {
1262  return(-1);
1263  }
1264  CHECK_COMPAT(buf)
1265  if ((buffer != NULL) && (buffer->content != NULL) &&
1266  (buffer->use > 0)) {
1267  ret = xmlBufAdd(buf, buffer->content, buffer->use);
1268  }
1270  return(ret);
1271 }
1272 
1282 int
1284  if ((input == NULL) || (buf == NULL) || (buf->error))
1285  return(-1);
1286  CHECK_COMPAT(buf)
1287  input->base = input->cur = buf->content;
1288  input->end = &buf->content[buf->use];
1289  return(0);
1290 }
1291 
1301 size_t
1303  size_t base;
1304 
1305  if ((input == NULL) || (buf == NULL) || (buf->error))
1306  return(-1);
1307  CHECK_COMPAT(buf)
1308  base = input->base - buf->content;
1309  /*
1310  * We could do some pointer arythmetic checks but that's probably
1311  * sufficient.
1312  */
1313  if (base > buf->size) {
1314  xmlBufOverflowError(buf, "Input reference outside of the buffer");
1315  base = 0;
1316  }
1317  return(base);
1318 }
1319 
1332 int
1334  size_t base, size_t cur) {
1335  if ((input == NULL) || (buf == NULL) || (buf->error))
1336  return(-1);
1337  CHECK_COMPAT(buf)
1338  input->base = &buf->content[base];
1339  input->cur = input->base + cur;
1340  input->end = &buf->content[buf->use];
1341  return(0);
1342 }
1343 
1344 #define bottom_buf
1345 #include "elfgcchack.h"
int xmlBufGrow(xmlBufPtr buf, int len)
Definition: buf.c:509
int xmlBufWriteChar(xmlBufPtr buf, const char *string)
Definition: buf.c:1088
size_t use
Definition: buf.c:49
xmlChar * xmlBufContent(const xmlBuf *buf)
Definition: buf.c:582
XMLPUBVAR xmlMallocFunc xmlMallocAtomic
Definition: globals.h:248
#define memmove(s1, s2, n)
Definition: mkisofs.h:881
static void xmlBufMemoryError(xmlBufPtr buf, const char *extra)
Definition: buf.c:92
int xmlBufSetInputBaseCur(xmlBufPtr buf, xmlParserInputPtr input, size_t base, size_t cur)
Definition: buf.c:1333
size_t xmlBufUse(const xmlBufPtr buf)
Definition: buf.c:687
xmlChar * contentIO
Definition: buf.c:48
xmlBufferAllocationScheme alloc
Definition: buf.c:47
#define INT_MAX
Definition: limits.h:40
static void xmlBufOverflowError(xmlBufPtr buf, const char *extra)
Definition: buf.c:107
int xmlBufAddLen(xmlBufPtr buf, size_t len)
Definition: buf.c:621
GLenum GLuint GLenum GLsizei const GLchar * buf
Definition: glext.h:7751
int xmlBufCat(xmlBufPtr buf, const xmlChar *str)
Definition: buf.c:1007
XMLPUBFUN int XMLCALL xmlStrlen(const xmlChar *str)
Definition: xmlstring.c:422
XMLPUBFUN void XMLCALL xmlBufferFree(xmlBufferPtr buf)
int xmlBufCCat(xmlBufPtr buf, const char *str)
Definition: buf.c:1027
#define CHECK_COMPAT(buf)
Definition: buf.c:71
xmlBufPtr xmlBufFromBuffer(xmlBufferPtr buffer)
Definition: buf.c:1167
DWORD scheme
GLuint buffer
Definition: glext.h:5915
size_t xmlBufLength(const xmlBufPtr buf)
Definition: buf.c:668
xmlBufPtr xmlBufCreateStatic(void *mem, size_t size)
Definition: buf.c:231
int xmlBufResetInput(xmlBufPtr buf, xmlParserInputPtr input)
Definition: buf.c:1283
#define XML_MAX_TEXT_LENGTH
_Check_return_opt_ _CRTIMP size_t __cdecl fwrite(_In_reads_bytes_(_Size *_Count) const void *_Str, _In_ size_t _Size, _In_ size_t _Count, _Inout_ FILE *_File)
XMLPUBFUN const xmlChar *XMLCALL xmlStrchr(const xmlChar *str, xmlChar val)
Definition: xmlstring.c:321
xmlChar * xmlBufDetach(xmlBufPtr buf)
Definition: buf.c:196
FILE * stdout
Definition: buf.c:43
#define UPDATE_COMPAT(buf)
Definition: buf.c:60
GLuint base
Definition: 3dtext.c:35
int xmlBufWriteCHAR(xmlBufPtr buf, const xmlChar *string)
Definition: buf.c:1067
xmlBufferAllocationScheme
Definition: tree.h:74
int xmlBufErase(xmlBufPtr buf, size_t len)
Definition: buf.c:646
XMLPUBVAR xmlGenericErrorFunc xmlGenericError
Definition: globals.h:346
xmlBufPtr xmlBufCreateSize(size_t size)
Definition: buf.c:156
const WCHAR * str
void xmlBufEmpty(xmlBufPtr buf)
Definition: buf.c:355
smooth NULL
Definition: ftsmooth.c:416
void xmlBufFree(xmlBufPtr buf)
Definition: buf.c:329
unsigned int compat_use
Definition: buf.c:45
#define BAD_CAST
Definition: xmlstring.h:35
xmlBuf * xmlBufPtr
Definition: tree.h:114
XMLPUBVAR xmlReallocFunc xmlRealloc
Definition: globals.h:249
GLsizeiptr size
Definition: glext.h:5919
Definition: id3.c:18
if(!(yy_init))
Definition: macro.lex.yy.c:714
int xmlBufIsEmpty(const xmlBufPtr buf)
Definition: buf.c:726
size_t xmlBufDump(FILE *file, xmlBufPtr buf)
Definition: buf.c:548
size_t xmlBufShrink(xmlBufPtr buf, size_t len)
Definition: buf.c:388
XMLPUBVAR xmlFreeFunc xmlFree
Definition: globals.h:250
int xmlBufAdd(xmlBufPtr buf, const xmlChar *str, int len)
Definition: buf.c:868
int xmlBufInflate(xmlBufPtr buf, size_t len)
Definition: buf.c:531
size_t size
Definition: buf.c:50
int ret
size_t xmlBufGetInputBase(xmlBufPtr buf, xmlParserInputPtr input)
Definition: buf.c:1302
xmlBufferPtr xmlBufBackToBuffer(xmlBufPtr buf)
Definition: buf.c:1204
unsigned char xmlChar
Definition: xmlstring.h:28
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
GLenum GLsizei len
Definition: glext.h:6722
size_t xmlBufAvail(const xmlBufPtr buf)
Definition: buf.c:708
static size_t xmlBufGrowInternal(xmlBufPtr buf, size_t len)
Definition: buf.c:437
xmlBufPtr xmlBufCreate(void)
Definition: buf.c:122
xmlBufferPtr buffer
Definition: buf.c:51
char string[160]
Definition: util.h:11
int xmlBufGetAllocationScheme(xmlBufPtr buf)
Definition: buf.c:267
int xmlBufSetAllocationScheme(xmlBufPtr buf, xmlBufferAllocationScheme scheme)
Definition: buf.c:288
#define UINT_MAX
Definition: limits.h:41
#define BASE_BUFFER_SIZE
Definition: tree.h:56
GLenum GLenum GLenum input
Definition: glext.h:9031
xmlChar * xmlBufEnd(xmlBufPtr buf)
Definition: buf.c:600
xmlChar * content
Definition: buf.c:44
int xmlBufResize(xmlBufPtr buf, size_t size)
Definition: buf.c:745
XMLPUBVAR xmlMallocFunc xmlMalloc
Definition: globals.h:247
XMLPUBVAR int xmlDefaultBufferSize
Definition: globals.h:312
int xmlBufMergeBuffer(xmlBufPtr buf, xmlBufferPtr buffer)
Definition: buf.c:1257
Definition: mem.c:156
int error
Definition: buf.c:52
int xmlBufAddHead(xmlBufPtr buf, const xmlChar *str, int len)
Definition: buf.c:928
unsigned int compat_size
Definition: buf.c:46
XMLPUBVAR xmlBufferAllocationScheme xmlBufferAllocScheme
Definition: globals.h:302
int xmlBufWriteQuotedString(xmlBufPtr buf, const xmlChar *string)
Definition: buf.c:1111
unsigned int(__cdecl typeof(jpeg_read_scanlines))(struct jpeg_decompress_struct *
Definition: typeof.h:31
XMLPUBVAR void * xmlGenericErrorContext
Definition: globals.h:362
Definition: fci.c:126