rpm 5.2.1

- Main Page
- Related Pages
- Modules
- Data Structures
- Files

- File List
- Globals

rpmio_internal.h
Go to the documentation of this file.
1 #ifndef H_RPMIO_INTERNAL
2 #define H_RPMIO_INTERNAL
3
8 #include <rpmiotypes.h>
9 #include <rpmlog.h>
10 #include <rpmio.h>
11 #include <rpmurl.h>
12
13 #define _RPMPGP_INTERNAL
14 #include <rpmpgp.h>
15
16 #include <rpmxar.h>
17
18 /*@access pgpDig @*/ /* XXX FIXME: (by refactoring to foo.c) */
19 /*@access rpmxar @*/ /* XXX FIXME: (by refactoring to foo.c) */
20
23 typedef struct _FDSTACK_s {
24 /*@exposed@*/
25 FDIO_t io;
26 /*@dependent@*/
27 void * fp;
28 int fdno;
29 } FDSTACK_t;
30
34 typedef enum fdOpX_e {
35 FDSTAT_READ = 0,
36 FDSTAT_WRITE = 1,
37 FDSTAT_SEEK = 2,
38 FDSTAT_CLOSE = 3,
39 FDSTAT_DIGEST = 4,
40 FDSTAT_MAX = 5
41 } fdOpX;
42
46 typedef /*@abstract@*/ struct {
47 struct rpmop_s ops[FDSTAT_MAX];
48 } * FDSTAT_t;
49
52 typedef struct _FDDIGEST_s {
53 pgpHashAlgo hashalgo;
54 DIGEST_CTX hashctx;
55 } * FDDIGEST_t;
56
60 struct _FD_s {
61 struct rpmioItem_s _item;
62 int flags;
63 #define RPMIO_DEBUG_IO 0x40000000
64 #define RPMIO_DEBUG_REFS 0x20000000
65 int magic;
66 #define FDMAGIC 0x04463138
67 int nfps;
68 FDSTACK_t fps[8];
69 int urlType; /* ufdio: */
70
71 /*@dependent@*/ /*@relnull@*/
72 void * url; /* ufdio: URL info */
73 /*@relnull@*/
74 void * req; /* ufdio: HTTP request */
75
76 int rd_timeoutsecs; /* ufdRead: per FD_t timer */
77 ssize_t bytesRemain; /* ufdio: */
78 ssize_t contentLength; /* ufdio: */
79 int persist; /* ufdio: */
80 int wr_chunked; /* ufdio: */
81
82 int syserrno; /* last system errno encountered */
83 /*@observer@*/
84 const void *errcookie; /* gzdio/bzdio/ufdio: */
85
86 /*null@*/
87 const char *opath; /* open(2) args. */
88 int oflags;
89 mode_t omode;
90
91 /*@refcounted@*/ /*@relnull@*/
92 rpmxar xar; /* xar archive wrapper */
93 /*@refcounted@*/ /*@relnull@*/
94 pgpDig dig; /* signature parameters */
95
96 FDSTAT_t stats; /* I/O statistics */
97
98 int ndigests;
99 #define FDDIGEST_MAX 32
100 struct _FDDIGEST_s digests[FDDIGEST_MAX];
101
102 /*null@*/
103 const char *contentType; /* ufdio: (HTTP) */
104 /*null@*/
105 const char *contentDisposition; /* ufdio: (HTTP) */
106 time_t lastModified; /* ufdio: (HTTP) */
107 int ftpFileDoneNeeded; /* ufdio: (FTP) */
108 unsigned long long fd_cpioPos; /* cpio: */
109 #if defined(__LCLINT__)
110 /*@refs@*/
111 int nrefs;
112 #endif
113 };
114 /*@access FD_t@*/
115
116 #define FDSANE(fd) assert(fd != NULL && fd->magic == FDMAGIC)
117
118 /*@-redecl@*/
119 /*@unchecked@*/
120 extern int _rpmio_debug;
121 /*@=redecl@*/
122
123 /*@-redecl@*/
124 /*@unchecked@*/
125 extern int _av_debug;
126 /*@=redecl@*/
127
128 /*@-redecl@*/
129 /*@unchecked@*/
130 extern int _ftp_debug;
131 /*@=redecl@*/
132
133 /*@-redecl@*/
134 /*@unchecked@*/
135 extern int _dav_debug;
136 /*@=redecl@*/
137
138 #define DBG(_f, _m, _x) \
139 /*@-modfilesys@*/ \
140 if ((_rpmio_debug | ((_f) ? ((FD_t)(_f))->flags : 0)) & (_m)) fprintf _x \
141 /*@=modfilesys@*/
142
143 #if defined(__LCLINT__XXX)
144 #define DBGIO(_f, _x)
145 #define DBGREFS(_f, _x)
146 #else
147 #define DBGIO(_f, _x) DBG((_f), RPMIO_DEBUG_IO, _x)
148 #define DBGREFS(_f, _x) DBG((_f), RPMIO_DEBUG_REFS, _x)
149 #endif
150
151 #ifdef __cplusplus
152 extern "C" {
153 #endif
154
157 /*@observer@*/ const char * fdbg(/*@null@*/ FD_t fd)
158 /*@*/;
159
162 int fdFgets(FD_t fd, char * buf, size_t len)
163 /*@globals errno, fileSystem @*/
164 /*@modifies *buf, fd, errno, fileSystem @*/;
165
168 /*@null@*/ FD_t ftpOpen(const char *url, /*@unused@*/ int flags,
169 /*@unused@*/ mode_t mode, /*@out@*/ urlinfo *uret)
170 /*@globals h_errno, fileSystem, internalState @*/
171 /*@modifies *uret, fileSystem, internalState @*/;
172
175 int ftpReq(FD_t data, const char * ftpCmd, const char * ftpArg)
176 /*@globals fileSystem, internalState @*/
177 /*@modifies data, fileSystem, internalState @*/;
178
181 int ftpCmd(const char * cmd, const char * url, const char * arg2)
182 /*@globals h_errno, fileSystem, internalState @*/
183 /*@modifies fileSystem, internalState @*/;
184
187 int ufdClose( /*@only@*/ void * cookie)
188 /*@globals fileSystem, internalState @*/
189 /*@modifies cookie, fileSystem, internalState @*/;
190
193 /*@unused@*/ static inline
194 void fdSetOpen(FD_t fd, const char * path, int flags, mode_t mode)
195 /*@modifies fd @*/
196 {
197 FDSANE(fd);
198 if (fd->opath != NULL) {
199 free((void *)fd->opath);
200 fd->opath = NULL;
201 }
202 fd->opath = xstrdup(path);
203 fd->oflags = flags;
204 fd->omode = mode;
205 }
206
209 /*@unused@*/ static inline
210 /*@null@*/ /*@observer@*/ const char * fdGetOPath(FD_t fd)
211 /*@*/
212 {
213 FDSANE(fd);
214 return fd->opath;
215 }
216
219 /*@unused@*/ static inline
220 int fdGetOFlags(FD_t fd)
221 /*@*/
222 {
223 FDSANE(fd);
224 return fd->oflags;
225 }
226
229 /*@unused@*/ static inline
230 mode_t fdGetOMode(FD_t fd)
231 /*@*/
232 {
233 FDSANE(fd);
234 return fd->omode;
235 }
236
239 /*@unused@*/ static inline
240 void fdSetDig(FD_t fd, pgpDig dig)
241 /*@globals fileSystem @*/
242 /*@modifies fd, dig, fileSystem @*/
243 {
244 FDSANE(fd);
245 /*@-assignexpose -castexpose @*/
246 fd->dig = pgpDigFree(fd->dig, "fdSetDig");
247 fd->dig = pgpDigLink(dig, "fdSetDig");
248 /*@=assignexpose =castexpose @*/
249 }
250
253 /*@unused@*/ static inline
254 /*@null@*/ pgpDig fdGetDig(FD_t fd)
255 /*@*/
256 {
257 FDSANE(fd);
258 /*@-compdef -retexpose -refcounttrans -usereleased @*/
259 return fd->dig;
260 /*@=compdef =retexpose =refcounttrans =usereleased @*/
261 }
262
265 /*@unused@*/ static inline
266 void fdSetXAR(FD_t fd, rpmxar xar)
267 /*@globals fileSystem @*/
268 /*@modifies fd, xar, fileSystem @*/
269 {
270 FDSANE(fd);
271 /*@-assignexpose -castexpose @*/
272 fd->xar = rpmxarLink(xar, "fdSetXAR");
273 /*@=assignexpose =castexpose @*/
274 }
275
278 /*@unused@*/ static inline
279 /*@null@*/ rpmxar fdGetXAR(FD_t fd)
280 /*@*/
281 {
282 FDSANE(fd);
283 /*@-compdef -refcounttrans -retexpose -usereleased @*/
284 return fd->xar;
285 /*@=compdef =refcounttrans =retexpose =usereleased @*/
286 }
287
290 /*@unused@*/ static inline
291 /*@null@*/ FDIO_t fdGetIo(FD_t fd)
292 /*@*/
293 {
294 FDSANE(fd);
295 return fd->fps[fd->nfps].io;
296 }
297
300 /*@-nullstate@*/ /* FIX: io may be NULL */
301 /*@unused@*/ static inline
302 void fdSetIo(FD_t fd, /*@kept@*/ /*@null@*/ FDIO_t io)
303 /*@modifies fd @*/
304 {
305 FDSANE(fd);
306 /*@-assignexpose@*/
307 fd->fps[fd->nfps].io = io;
308 /*@=assignexpose@*/
309 }
310 /*@=nullstate@*/
311
314 /*@unused@*/ static inline
315 /*@exposed@*/ /*@dependent@*/ /*@null@*/ FILE * fdGetFILE(FD_t fd)
316 /*@*/
317 {
318 FDSANE(fd);
319 /*@+voidabstract@*/
320 return ((FILE *)fd->fps[fd->nfps].fp);
321 /*@=voidabstract@*/
322 }
323
326 /*@unused@*/ static inline
327 /*@exposed@*/ /*@dependent@*/ /*@null@*/ void * fdGetFp(FD_t fd)
328 /*@*/
329 {
330 FDSANE(fd);
331 return fd->fps[fd->nfps].fp;
332 }
333
336 /*@-nullstate@*/ /* FIX: fp may be NULL */
337 /*@unused@*/ static inline
338 void fdSetFp(FD_t fd, /*@kept@*/ /*@null@*/ void * fp)
339 /*@modifies fd @*/
340 {
341 FDSANE(fd);
342 /*@-assignexpose@*/
343 fd->fps[fd->nfps].fp = fp;
344 /*@=assignexpose@*/
345 }
346 /*@=nullstate@*/
347
350 /*@unused@*/ static inline
351 int fdGetFdno(FD_t fd)
352 /*@*/
353 {
354 FDSANE(fd);
355 return fd->fps[fd->nfps].fdno;
356 }
357
360 /*@unused@*/ static inline
361 void fdSetFdno(FD_t fd, int fdno)
362 /*@modifies fd @*/
363 {
364 FDSANE(fd);
365 fd->fps[fd->nfps].fdno = fdno;
366 }
367
370 /*@unused@*/ static inline
371 void fdSetContentLength(FD_t fd, ssize_t contentLength)
372 /*@modifies fd @*/
373 {
374 FDSANE(fd);
375 fd->contentLength = fd->bytesRemain = contentLength;
376 }
377
380 /*@unused@*/ static inline
381 void fdPush(FD_t fd, FDIO_t io, void * fp, int fdno)
382 /*@modifies fd @*/
383 {
384 FDSANE(fd);
385 if (fd->nfps >= (int)(sizeof(fd->fps)/sizeof(fd->fps[0]) - 1))
386 return;
387 fd->nfps++;
388 fdSetIo(fd, io);
389 fdSetFp(fd, fp);
390 fdSetFdno(fd, fdno);
391 }
392
395 /*@unused@*/ static inline
396 void fdPop(FD_t fd)
397 /*@modifies fd @*/
398 {
399 FDSANE(fd);
400 if (fd->nfps < 0) return;
401 fdSetIo(fd, NULL);
402 fdSetFp(fd, NULL);
403 fdSetFdno(fd, -1);
404 fd->nfps--;
405 }
406
409 /*@unused@*/ static inline /*@null@*/
410 rpmop fdstat_op(/*@null@*/ FD_t fd, fdOpX opx)
411 /*@*/
412 {
413 rpmop op = NULL;
414
415 if (fd != NULL && fd->stats != NULL && (int)opx >= 0 && opx < FDSTAT_MAX)
416 op = fd->stats->ops + opx;
417 return op;
418 }
419
422 /*@unused@*/ static inline
423 void fdstat_enter(/*@null@*/ FD_t fd, int opx)
424 /*@globals internalState @*/
425 /*@modifies internalState @*/
426 {
427 if (fd == NULL) return;
428 if (fd->stats != NULL)
429 (void) rpmswEnter(fdstat_op(fd, opx), 0);
430 }
431
434 /*@unused@*/ static inline
435 void fdstat_exit(/*@null@*/ FD_t fd, int opx, ssize_t rc)
436 /*@globals internalState @*/
437 /*@modifies fd, internalState @*/
438 {
439 if (fd == NULL) return;
440 if (rc == -1)
441 fd->syserrno = errno;
442 else if (rc > 0 && fd->bytesRemain > 0)
443 switch (opx) {
444 case FDSTAT_READ:
445 case FDSTAT_WRITE:
446 fd->bytesRemain -= rc;
447 break;
448 default:
449 break;
450 }
451 if (fd->stats != NULL)
452 (void) rpmswExit(fdstat_op(fd, opx), rc);
453 }
454
457 /*@unused@*/ static inline
458 void fdstat_print(/*@null@*/ FD_t fd, const char * msg, FILE * fp)
459 /*@globals fileSystem @*/
460 /*@modifies *fp, fileSystem @*/
461 {
462 static int usec_scale = (1000*1000);
463 int opx;
464
465 if (fd == NULL || fd->stats == NULL) return;
466 for (opx = 0; opx < 4; opx++) {
467 rpmop op = &fd->stats->ops[opx];
468 if (op->count <= 0) continue;
469 switch (opx) {
470 case FDSTAT_READ:
471 if (msg != NULL) fprintf(fp, "%s:", msg);
472 fprintf(fp, "%8d reads, %8lu total bytes in %d.%06d secs\n",
473 op->count, (unsigned long)op->bytes,
474 (int)(op->usecs/usec_scale), (int)(op->usecs%usec_scale));
475 /*@switchbreak@*/ break;
476 case FDSTAT_WRITE:
477 if (msg != NULL) fprintf(fp, "%s:", msg);
478 fprintf(fp, "%8d writes, %8lu total bytes in %d.%06d secs\n",
479 op->count, (unsigned long)op->bytes,
480 (int)(op->usecs/usec_scale), (int)(op->usecs%usec_scale));
481 /*@switchbreak@*/ break;
482 case FDSTAT_SEEK:
483 /*@switchbreak@*/ break;
484 case FDSTAT_CLOSE:
485 /*@switchbreak@*/ break;
486 }
487 }
488 }
489
492 /*@unused@*/ static inline
493 void fdSetSyserrno(FD_t fd, int syserrno, /*@kept@*/ const void * errcookie)
494 /*@modifies fd @*/
495 {
496 FDSANE(fd);
497 fd->syserrno = syserrno;
498 /*@-assignexpose@*/
499 fd->errcookie = errcookie;
500 /*@=assignexpose@*/
501 }
502
505 /*@unused@*/ static inline
506 int fdGetRdTimeoutSecs(FD_t fd)
507 /*@*/
508 {
509 FDSANE(fd);
510 return fd->rd_timeoutsecs;
511 }
512
515 /*@unused@*/ static inline
516 unsigned long long fdGetCpioPos(FD_t fd)
517 /*@*/
518 {
519 FDSANE(fd);
520 return fd->fd_cpioPos;
521 }
522
525 /*@unused@*/ static inline
526 void fdSetCpioPos(FD_t fd, long int cpioPos)
527 /*@modifies fd @*/
528 {
529 FDSANE(fd);
530 fd->fd_cpioPos = cpioPos;
531 }
532
535 /*@mayexit@*/ /*@unused@*/ static inline
536 FD_t c2f(/*@null@*/ void * cookie)
537 /*@*/
538 {
539 /*@-castexpose@*/
540 FD_t fd = (FD_t) cookie;
541 /*@=castexpose@*/
542 FDSANE(fd);
543 /*@-refcounttrans -retalias@*/ return fd; /*@=refcounttrans =retalias@*/
544 }
545
549 /*@unused@*/ static inline
550 void fdInitDigest(FD_t fd, pgpHashAlgo hashalgo, int flags)
551 /*@globals internalState @*/
552 /*@modifies fd, internalState @*/
553 {
554 FDDIGEST_t fddig = fd->digests + fd->ndigests;
555 if (fddig != (fd->digests + FDDIGEST_MAX)) {
556 fd->ndigests++;
557 fddig->hashalgo = hashalgo;
558 fdstat_enter(fd, FDSTAT_DIGEST);
559 fddig->hashctx = rpmDigestInit(hashalgo, flags);
560 fdstat_exit(fd, FDSTAT_DIGEST, 0);
561 }
562 }
563
567 /*@unused@*/ static inline
568 void fdUpdateDigests(FD_t fd, const unsigned char * buf, ssize_t buflen)
569 /*@globals internalState @*/
570 /*@modifies fd, internalState @*/
571 {
572 int i;
573
574 if (buf != NULL && buflen > 0)
575 for (i = fd->ndigests - 1; i >= 0; i--) {
576 FDDIGEST_t fddig = fd->digests + i;
577 if (fddig->hashctx == NULL)
578 continue;
579 fdstat_enter(fd, FDSTAT_DIGEST);
580 (void) rpmDigestUpdate(fddig->hashctx, buf, buflen);
581 fdstat_exit(fd, FDSTAT_DIGEST, buflen);
582 }
583 }
584
587 /*@unused@*/ static inline
588 void fdFiniDigest(FD_t fd, pgpHashAlgo hashalgo,
589 /*@null@*/ /*@out@*/ void * datap,
590 /*@null@*/ /*@out@*/ size_t * lenp,
591 int asAscii)
592 /*@globals internalState @*/
593 /*@modifies fd, *datap, *lenp, internalState @*/
594 {
595 int imax = -1;
596 int i;
597
598 for (i = fd->ndigests - 1; i >= 0; i--) {
599 FDDIGEST_t fddig = fd->digests + i;
600 if (fddig->hashctx == NULL)
601 continue;
602 if (i > imax) imax = i;
603 if (fddig->hashalgo != hashalgo)
604 continue;
605 fdstat_enter(fd, FDSTAT_DIGEST);
606 (void) rpmDigestFinal(fddig->hashctx, datap, lenp, asAscii);
607 fdstat_exit(fd, FDSTAT_DIGEST, 0);
608 fddig->hashctx = NULL;
609 break;
610 }
611 if (i < 0) {
612 if (datap != NULL) *(void **)datap = NULL;
613 if (lenp != NULL) *lenp = 0;
614 }
615
616 fd->ndigests = imax;
617 if (i < imax)
618 fd->ndigests++; /* convert index to count */
619 }
620
623 /*@-mustmod@*/
624 /*@unused@*/ static inline
625 void fdStealDigest(FD_t fd, pgpDig dig)
626 /*@modifies fd, dig @*/
627 {
628 int i;
629 /*@-type@*/ /* FIX: getters for pgpDig internals */
630 for (i = fd->ndigests - 1; i >= 0; i--) {
631 FDDIGEST_t fddig = fd->digests + i;
632 if (fddig->hashctx != NULL)
633 switch (fddig->hashalgo) {
634 case PGPHASHALGO_MD5:
635 assert(dig->md5ctx == NULL);
636 /*@-onlytrans@*/
637 dig->md5ctx = fddig->hashctx;
638 /*@=onlytrans@*/
639 fddig->hashctx = NULL;
640 /*@switchbreak@*/ break;
641 case PGPHASHALGO_SHA1:
642 case PGPHASHALGO_RIPEMD160:
643 #if defined(HAVE_BEECRYPT_API_H)
644 case PGPHASHALGO_SHA256:
645 case PGPHASHALGO_SHA384:
646 case PGPHASHALGO_SHA512:
647 #endif
648 assert(dig->sha1ctx == NULL);
649 /*@-onlytrans@*/
650 dig->sha1ctx = fddig->hashctx;
651 /*@=onlytrans@*/
652 fddig->hashctx = NULL;
653 /*@switchbreak@*/ break;
654 default:
655 /*@switchbreak@*/ break;
656 }
657 }
658 /*@=type@*/
659 }
660 /*@=mustmod@*/
661
662 /*@-shadow@*/
665 /*@unused@*/ static inline
666 int fdFileno(/*@null@*/ void * cookie)
667 /*@*/
668 {
669 FD_t fd;
670 if (cookie == NULL) return -2;
671 fd = c2f(cookie);
672 return fd->fps[0].fdno;
673 }
674 /*@=shadow@*/
675
676 #ifdef __cplusplus
677 }
678 #endif
679
680 #endif /* H_RPMIO_INTERNAL */