rpm
5.2.1
|
00001 00004 #include "system.h" 00005 #define _RPMIOB_INTERNAL 00006 #include <rpmiotypes.h> 00007 #include <rpmio.h> 00008 #include "debug.h" 00009 00010 /*@unchecked@*/ 00011 size_t _rpmiob_chunk = 1024; 00012 00013 /*@unchecked@*/ 00014 int _rpmiob_debug; 00015 00016 static void rpmiobFini(void * _iob) 00017 { 00018 rpmiob iob = _iob; 00019 00020 iob->b = _free(iob->b); 00021 iob->blen = 0; 00022 iob->allocated = 0; 00023 } 00024 00025 /*@unchecked@*/ /*@only@*/ /*@null@*/ 00026 rpmioPool _rpmiobPool; 00027 00028 static rpmiob rpmiobGetPool(/*@null@*/ rpmioPool pool) 00029 /*@globals _rpmiobPool, fileSystem @*/ 00030 /*@modifies pool, _rpmiobPool, fileSystem @*/ 00031 { 00032 rpmiob iob; 00033 00034 if (_rpmiobPool == NULL) { 00035 _rpmiobPool = rpmioNewPool("iob", sizeof(*iob), -1, _rpmiob_debug, 00036 NULL, NULL, rpmiobFini); 00037 pool = _rpmiobPool; 00038 } 00039 return (rpmiob) rpmioGetPool(pool, sizeof(*iob)); 00040 } 00041 00042 rpmiob rpmiobNew(size_t len) 00043 { 00044 rpmiob iob = rpmiobGetPool(_rpmiobPool); 00045 if (len == 0) 00046 len = _rpmiob_chunk; 00047 iob->allocated = len; 00048 iob->blen = 0; 00049 iob->b = xcalloc(iob->allocated+1, sizeof(*iob->b)); 00050 return rpmiobLink(iob); 00051 } 00052 00053 rpmiob rpmiobEmpty(rpmiob iob) 00054 { 00055 assert(iob != NULL); 00056 iob->b[0] = '\0'; 00057 iob->blen = 0; 00058 return iob; 00059 } 00060 00061 rpmiob rpmiobRTrim(rpmiob iob) 00062 { 00063 00064 assert(iob != NULL); 00065 while (iob->blen > 0 && xisspace((int)iob->b[iob->blen-1])) 00066 iob->b[--iob->blen] = (rpmuint8_t) '\0'; 00067 return iob; 00068 } 00069 00070 rpmiob rpmiobAppend(rpmiob iob, const char * s, size_t nl) 00071 { 00072 size_t ns = strlen(s); 00073 rpmuint8_t * tail; 00074 00075 if (nl > 0) ns++; 00076 00077 assert(iob != NULL); 00078 if ((iob->blen + ns) > iob->allocated) { 00079 iob->allocated += ((ns+_rpmiob_chunk-1)/_rpmiob_chunk) * _rpmiob_chunk; 00080 iob->b = xrealloc(iob->b, iob->allocated+1); 00081 } 00082 00083 tail = iob->b + iob->blen; 00084 tail = (rpmuint8_t *) stpcpy((char *)tail, s); 00085 if (nl > 0) { 00086 *tail++ = (rpmuint8_t) '\n'; 00087 *tail = (rpmuint8_t) '\0'; 00088 } 00089 iob->blen += ns; 00090 return iob; 00091 } 00092 00093 rpmuint8_t * rpmiobBuf(rpmiob iob) 00094 { 00095 assert(iob != NULL); 00096 /*@-retalias -retexpose -usereleased @*/ 00097 return iob->b; 00098 /*@=retalias =retexpose =usereleased @*/ 00099 } 00100 00101 char * rpmiobStr(rpmiob iob) 00102 { 00103 assert(iob != NULL); 00104 /*@-retalias -retexpose -usereleased @*/ 00105 return (char *) iob->b; 00106 /*@=retalias =retexpose =usereleased @*/ 00107 } 00108 00109 size_t rpmiobLen(rpmiob iob) 00110 { 00111 return (iob != NULL ? iob->blen : 0); 00112 } 00113 00114 int rpmiobSlurp(const char * fn, rpmiob * iobp) 00115 { 00116 static size_t blenmax = (32 * BUFSIZ); 00117 rpmuint8_t * b = NULL; 00118 size_t blen; 00119 struct stat sb; 00120 FD_t fd; 00121 int rc = 0; 00122 int xx; 00123 00124 fd = Fopen(fn, "r%{?_rpmgio}"); 00125 if (fd == NULL || Ferror(fd)) { 00126 rc = 2; 00127 goto exit; 00128 } 00129 sb.st_size = 0; 00130 if ((xx = Fstat(fd, &sb)) < 0 || sb.st_size == 0) 00131 sb.st_size = blenmax; 00132 #if defined(__linux__) 00133 /* XXX st->st_size = 0 for /proc files on linux, see stat(2). */ 00134 /* XXX glibc mmap'd libio no workie for /proc files on linux?!? */ 00135 if (sb.st_size == 0 && !strncmp(fn, "/proc/", sizeof("/proc/")-1)) { 00136 blen = blenmax; 00137 b = xmalloc(blen+1); 00138 b[0] = (rpmuint8_t) '\0'; 00139 00140 xx = read(Fileno(fd), b, blen); 00141 blen = (size_t) (xx >= 0 ? xx : 0); 00142 } else 00143 #endif 00144 { 00145 blen = sb.st_size; 00146 b = xmalloc(blen+1); 00147 b[0] = (rpmuint8_t) '\0'; 00148 00149 blen = Fread(b, sizeof(*b), blen, fd); 00150 if (Ferror(fd)) { 00151 rc = 1; 00152 goto exit; 00153 } 00154 } 00155 if (blen < (size_t)sb.st_size) 00156 b = xrealloc(b, blen+1); 00157 b[blen] = (rpmuint8_t) '\0'; 00158 00159 exit: 00160 if (fd != NULL) (void) Fclose(fd); 00161 00162 if (rc == 0) { 00163 if (iobp != NULL) { 00164 /* XXX use rpmiobNew() if/when lazy iop->b alloc is implemented. */ 00165 rpmiob iob = rpmiobGetPool(_rpmiobPool); 00166 iob->b = b; 00167 iob->blen = blen; 00168 iob->allocated = blen; 00169 *iobp = iob; 00170 } 00171 } else { 00172 if (iobp) 00173 *iobp = NULL; 00174 b = _free(b); 00175 } 00176 00177 return rc; 00178 }