mirror of
git://git.gnupg.org/gnupg.git
synced 2025-07-02 22:46:30 +02:00
iobuf: Add the IOBUF_INPUT_TEMP type to improve input temp handling.
* common/iobuf.h (enum iobuf_use): Add new member, IOBUF_INPUT_TEMP. * common/iobuf.c (iobuf_temp_with_content): Create the iobuf as an IOBUF_INPUT_TEMP, not an IOBUF_INPUT buffer. Assert that LENGTH == A->D.SIZE. (iobuf_push_filter2): If A is an IOBUF_INPUT_TEMP, then make the new filter an IOBUF_INPUT filter and set its buffer size to IOBUF_BUFFER_SIZE. (underflow): If A is an IOBUF_INPUT_TEMP, then just return EOF; don't remove already read data. (iobuf_seek): If A is an IOBUF_INPUT_TEMP, don't discard the buffered data. (iobuf_alloc): Allow USE == IOBUF_INPUT_TEMP. (pop_filter): Allow USE == IOBUF_INPUT_TEMP. (iobuf_peek): Allow USE == IOBUF_INPUT_TEMP. (iobuf_writebyte): Fail if USE == IOBUF_INPUT_TEMP. (iobuf_write): Fail if USE == IOBUF_INPUT_TEMP. (iobuf_writestr): Fail if USE == IOBUF_INPUT_TEMP. (iobuf_flush_temp): Fail if USE == IOBUF_INPUT_TEMP. -- Signed-off-by: Neal H. Walfield <neal@g10code.com>. Introduce a new iobuf type, IOBUF_INPUT_TEMP. Use this for the iobuf created by iobuf_temp_with_content instead of IOBUF_INPUT. This was necessary so that seeking and peeking correctly work on this type of iobuf. In particular, seeking didn't work because we discarded the buffered data and peeking didn't work because we discarded data which was already read, which made seeking later impossible.
This commit is contained in:
parent
5ff5e72b9c
commit
f2d75ac7dc
2 changed files with 29 additions and 20 deletions
|
@ -1099,7 +1099,7 @@ iobuf_alloc (int use, size_t bufsize)
|
|||
iobuf_t a;
|
||||
static int number = 0;
|
||||
|
||||
assert (use == IOBUF_INPUT
|
||||
assert (use == IOBUF_INPUT || use == IOBUF_INPUT_TEMP
|
||||
|| use == IOBUF_OUTPUT || use == IOBUF_OUTPUT_TEMP);
|
||||
if (bufsize == 0)
|
||||
{
|
||||
|
@ -1220,7 +1220,8 @@ iobuf_temp_with_content (const char *buffer, size_t length)
|
|||
iobuf_t a;
|
||||
int i;
|
||||
|
||||
a = iobuf_alloc (IOBUF_INPUT, length);
|
||||
a = iobuf_alloc (IOBUF_INPUT_TEMP, length);
|
||||
assert (length == a->d.size);
|
||||
/* memcpy (a->d.buf, buffer, length); */
|
||||
for (i=0; i < length; i++)
|
||||
a->d.buf[i] = buffer[i];
|
||||
|
@ -1619,6 +1620,12 @@ iobuf_push_filter2 (iobuf_t a,
|
|||
size. */
|
||||
a->d.size = IOBUF_BUFFER_SIZE;
|
||||
}
|
||||
else if (a->use == IOBUF_INPUT_TEMP)
|
||||
/* Same idea as above. */
|
||||
{
|
||||
a->use = IOBUF_INPUT;
|
||||
a->d.size = IOBUF_BUFFER_SIZE;
|
||||
}
|
||||
|
||||
/* The new filter (A) gets a new buffer.
|
||||
|
||||
|
@ -1678,7 +1685,7 @@ pop_filter (iobuf_t a, int (*f) (void *opaque, int control,
|
|||
if (DBG_IOBUF)
|
||||
log_debug ("iobuf-%d.%d: pop '%s'\n",
|
||||
a->no, a->subno, iobuf_desc (a));
|
||||
if (a->use == IOBUF_OUTPUT_TEMP)
|
||||
if (a->use == IOBUF_INPUT_TEMP || a->use == IOBUF_OUTPUT_TEMP)
|
||||
{
|
||||
/* This should be the last filter in the pipeline. */
|
||||
assert (! a->chain);
|
||||
|
@ -1765,6 +1772,11 @@ underflow (iobuf_t a, int clear_pending_eof)
|
|||
(int) a->d.size, (int) (a->d.len - a->d.start),
|
||||
(int) (a->d.size - (a->d.len - a->d.start)));
|
||||
|
||||
if (a->use == IOBUF_INPUT_TEMP)
|
||||
/* By definition, there isn't more data to read into the
|
||||
buffer. */
|
||||
return -1;
|
||||
|
||||
assert (a->use == IOBUF_INPUT);
|
||||
|
||||
/* If there is still some buffered data, then move it to the start
|
||||
|
@ -2056,7 +2068,7 @@ iobuf_peek (iobuf_t a, byte * buf, unsigned buflen)
|
|||
int n = 0;
|
||||
|
||||
assert (buflen > 0);
|
||||
assert (a->use == IOBUF_INPUT);
|
||||
assert (a->use == IOBUF_INPUT || a->use == IOBUF_INPUT_TEMP);
|
||||
|
||||
if (buflen > a->d.size)
|
||||
/* We can't peek more than we can buffer. */
|
||||
|
@ -2097,7 +2109,7 @@ iobuf_writebyte (iobuf_t a, unsigned int c)
|
|||
{
|
||||
int rc;
|
||||
|
||||
if (a->use == IOBUF_INPUT)
|
||||
if (a->use == IOBUF_INPUT || a->use == IOBUF_INPUT_TEMP)
|
||||
{
|
||||
log_bug ("iobuf_writebyte called on an input pipeline!\n");
|
||||
return -1;
|
||||
|
@ -2119,7 +2131,7 @@ iobuf_write (iobuf_t a, const void *buffer, unsigned int buflen)
|
|||
const unsigned char *buf = (const unsigned char *)buffer;
|
||||
int rc;
|
||||
|
||||
if (a->use == IOBUF_INPUT)
|
||||
if (a->use == IOBUF_INPUT || a->use == IOBUF_INPUT_TEMP)
|
||||
{
|
||||
log_bug ("iobuf_write called on an input pipeline!\n");
|
||||
return -1;
|
||||
|
@ -2152,7 +2164,7 @@ iobuf_write (iobuf_t a, const void *buffer, unsigned int buflen)
|
|||
int
|
||||
iobuf_writestr (iobuf_t a, const char *buf)
|
||||
{
|
||||
if (a->use == IOBUF_INPUT)
|
||||
if (a->use == IOBUF_INPUT || a->use == IOBUF_INPUT_TEMP)
|
||||
{
|
||||
log_bug ("iobuf_writestr called on an input pipeline!\n");
|
||||
return -1;
|
||||
|
@ -2200,7 +2212,7 @@ iobuf_temp_to_buffer (iobuf_t a, byte * buffer, size_t buflen)
|
|||
void
|
||||
iobuf_flush_temp (iobuf_t temp)
|
||||
{
|
||||
if (temp->use == IOBUF_INPUT)
|
||||
if (temp->use == IOBUF_INPUT || temp->use == IOBUF_INPUT_TEMP)
|
||||
log_bug ("iobuf_writestr called on an input pipeline!\n");
|
||||
while (temp->chain)
|
||||
pop_filter (temp, temp->filter, NULL);
|
||||
|
@ -2379,10 +2391,9 @@ iobuf_seek (iobuf_t a, off_t newpos)
|
|||
return -1;
|
||||
}
|
||||
#endif
|
||||
/* Discard the buffer it is not a temp stream. */
|
||||
a->d.len = 0;
|
||||
}
|
||||
/* Discard the buffer it is not a temp stream. */
|
||||
if (a->use != IOBUF_OUTPUT_TEMP)
|
||||
a->d.len = 0;
|
||||
a->d.start = 0;
|
||||
a->nbytes = 0;
|
||||
a->nlimit = 0;
|
||||
|
@ -2409,10 +2420,6 @@ iobuf_seek (iobuf_t a, off_t newpos)
|
|||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
const char *
|
||||
iobuf_get_real_fname (iobuf_t a)
|
||||
{
|
||||
|
@ -2430,7 +2437,6 @@ iobuf_get_real_fname (iobuf_t a)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
|
||||
const char *
|
||||
iobuf_get_fname (iobuf_t a)
|
||||
{
|
||||
|
@ -2462,7 +2468,6 @@ iobuf_set_partial_block_mode (iobuf_t a, size_t len)
|
|||
{
|
||||
block_filter_ctx_t *ctx = xcalloc (1, sizeof *ctx);
|
||||
|
||||
assert (a->use == IOBUF_INPUT || a->use == IOBUF_OUTPUT);
|
||||
ctx->use = a->use;
|
||||
if (!len)
|
||||
{
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue