mng_write() and large file (was: mng_display_gotime() and large files)
Evgeniy Rigkov <[email protected]> Tue, 27 Jul 2004 01:08:16 +0400
| Newsgroups | gmane.comp.graphics.mng.general |
|---|---|
| Message-ID | <[email protected]> |
GJ> That way you keep the order of the chunks correct. libmng will can
GJ> expect an IHDR after the previous IEND. Doesn't matter to libmng
GJ> if it's coming from a previous part of the input-stream.
I made this in readdata callback (summarily):
mng_bool my_readdata(mng_handle mng, mng_ptr buffer,
mng_uint32 size, mng_uint32 *bytesread)
{
*bytesread = fread(buffer, 1, size, mymng->file);
// read IHDR chunk ?
if (strstr((char*) buffer, "IHDR"))
{
if (need_rewind)
{
fseek(mymng->file, requisite_ihdr_filepos, SEEK_SET);
*bytesread = fread(buffer, 1, size, mymng->file);
}
}
return MNG_TRUE;
}
Although this works for my task, yet it's not universal :-(.
But then i have other problem with mng_write() and large files.
All chunks store in memory, and at the end write once on disk.
I think, what it is not correct, because if file is large... :-).
Can i write chunks immediately after putchunk() ?
I.e. i want write
for (i = 1; i <= frames; i++)
{
mng_putchunk_ihdr();
mng_putchunk_idat();
mng_putchunk_iend();
mng_write();
mng_drop_chunks();
}
instead
for (i = 1; i <= frames; i++)
{
mng_putchunk_ihdr();
mng_putchunk_idat();
mng_putchunk_iend();
}
mng_write();
Now i have few patches for libmng-1.0.7, which allow this.
Please, see them. May be possible include their in the libmng distribution?
I shall remind my MNG structure: much IHDR, IDAT, IEND sequences.
-------------------libmng_chunk_xs.c.diff begin ----------------------
*** libmng_chunk_xs.c Sun Mar 21 21:18:13 2004
--- libmng_chunk_xs.c Wed Jul 14 16:34:49 2004
***************
*** 2538,2550 ****
mng_add_chunk (pData, pChunk); /* add it to the list */
! #ifdef MNG_INCLUDE_JNG
! if ((pData->iFirstchunkadded == MNG_UINT_IHDR) ||
! (pData->iFirstchunkadded == MNG_UINT_JHDR) )
! #else
! if (pData->iFirstchunkadded == MNG_UINT_IHDR)
! #endif
! pData->bCreating = MNG_FALSE; /* should be last chunk !!! */
#ifdef MNG_SUPPORT_TRACE
MNG_TRACE (((mng_datap)hHandle), MNG_FN_PUTCHUNK_IEND, MNG_LC_END)
--- 2538,2550 ----
mng_add_chunk (pData, pChunk); /* add it to the list */
! //#ifdef MNG_INCLUDE_JNG
! // if ((pData->iFirstchunkadded == MNG_UINT_IHDR) ||
! // (pData->iFirstchunkadded == MNG_UINT_JHDR) )
! //#else
! // if (pData->iFirstchunkadded == MNG_UINT_IHDR)
! //#endif
! // pData->bCreating = MNG_FALSE; /* should be last chunk !!! */
#ifdef MNG_SUPPORT_TRACE
MNG_TRACE (((mng_datap)hHandle), MNG_FN_PUTCHUNK_IEND, MNG_LC_END)
-------------------libmng_chunk_xs.c.diff end ----------------------
-------------------libmng_hlapi.c.diff begin -----------------------
*** libmng_hlapi.c Sun Mar 21 21:18:16 2004
--- libmng_hlapi.c Wed Jul 14 16:39:11 2004
***************
*** 223,228 ****
--- 223,231 ----
pChunk = pNext; /* neeeext */
}
+ pData->pFirstchunk = MNG_NULL;
+ pData->pLastchunk = MNG_NULL;
+
#ifdef MNG_SUPPORT_TRACE
MNG_TRACE (pData, MNG_FN_DROP_CHUNKS, MNG_LC_END)
#endif
***************
*** 1922,1929 ****
MNG_ERROR (pData, MNG_FUNCTIONINVALID)
#endif
! if (pData->bCreating) /* can't write while it's still being made! */
! MNG_ERROR (pData, MNG_FUNCTIONINVALID)
cleanup_errors (pData); /* cleanup previous errors */
--- 1925,1932 ----
MNG_ERROR (pData, MNG_FUNCTIONINVALID)
#endif
! // if (pData->bCreating) /* can't write while it's still being made! */
! // MNG_ERROR (pData, MNG_FUNCTIONINVALID)
cleanup_errors (pData); /* cleanup previous errors */
-------------------libmng_hlapi.c.diff end ------------------------
-------------------libmng_write.c.diff begin ----------------------
*** libmng_write.c Sun Mar 21 21:18:20 2004
--- libmng_write.c Wed Jul 14 16:43:00 2004
***************
*** 76,104 ****
pData->iWritebufsize = 32768; /* get a temporary write buffer */
/* reserve 12 bytes for length, chunkname & crc */
MNG_ALLOC (pData, pData->pWritebuf, pData->iWritebufsize+12)
/* write the signature */
! if (((mng_chunk_headerp)pChunk)->iChunkname == MNG_UINT_IHDR)
! mng_put_uint32 (pData->pWritebuf, PNG_SIG);
! else
! if (((mng_chunk_headerp)pChunk)->iChunkname == MNG_UINT_JHDR)
! mng_put_uint32 (pData->pWritebuf, JNG_SIG);
! else
! mng_put_uint32 (pData->pWritebuf, MNG_SIG);
! mng_put_uint32 (pData->pWritebuf+4, POST_SIG);
! if (!pData->fWritedata ((mng_handle)pData, pData->pWritebuf, 8, &iWritten))
! {
! MNG_FREE (pData, pData->pWritebuf, pData->iWritebufsize+12)
! MNG_ERROR (pData, MNG_APPIOERROR)
! }
! if (iWritten != 8) /* disk full ? */
! {
! MNG_FREE (pData, pData->pWritebuf, pData->iWritebufsize+12)
! MNG_ERROR (pData, MNG_OUTPUTERROR)
}
!
while (pChunk) /* so long as there's something to write */
{ /* let's call it's output routine */
iRetcode = ((mng_chunk_headerp)pChunk)->fWrite (pData, pChunk);
--- 76,108 ----
pData->iWritebufsize = 32768; /* get a temporary write buffer */
/* reserve 12 bytes for length, chunkname & crc */
MNG_ALLOC (pData, pData->pWritebuf, pData->iWritebufsize+12)
+
+ if (((mng_chunk_headerp)pChunk)->iChunkname == MNG_UINT_MHDR)
+ {
/* write the signature */
! if (((mng_chunk_headerp)pChunk)->iChunkname == MNG_UINT_IHDR)
! mng_put_uint32 (pData->pWritebuf, PNG_SIG);
! else
! if (((mng_chunk_headerp)pChunk)->iChunkname == MNG_UINT_JHDR)
! mng_put_uint32 (pData->pWritebuf, JNG_SIG);
! else
! mng_put_uint32 (pData->pWritebuf, MNG_SIG);
! mng_put_uint32 (pData->pWritebuf+4, POST_SIG);
! if (!pData->fWritedata ((mng_handle)pData, pData->pWritebuf, 8, &iWritten))
! {
! MNG_FREE (pData, pData->pWritebuf, pData->iWritebufsize+12)
! MNG_ERROR (pData, MNG_APPIOERROR)
! }
! if (iWritten != 8) /* disk full ? */
! {
! MNG_FREE (pData, pData->pWritebuf, pData->iWritebufsize+12)
! MNG_ERROR (pData, MNG_OUTPUTERROR)
! }
}
!
while (pChunk) /* so long as there's something to write */
{ /* let's call it's output routine */
iRetcode = ((mng_chunk_headerp)pChunk)->fWrite (pData, pChunk);
-------------------libmng_write.c.diff end ------------------------
--
Send the message body "help" to [email protected]