Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations Chriss Miller on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

ReadAll() fails 3

Status
Not open for further replies.

rmusgrove

Programmer
Mar 12, 2003
43
US
Anyone ever seen this before?

I have a piece of code I use to get the dimensions of various kinds of image files (gif, jpeg, etc). For the gif file format, this is particularly simple: the width is stored in bytes 7-6, the height in bytes 9-8. The following code should extract the gif header:

path = "mygif.gif"
mappedPath = Server.MapPath(path)
Set fs = Server.CreateObject("Scripting.FileSystemObject")
If fs.FileExists(mappedPath) Then
set lStream = fs.OpenTextFile(mappedPath)
s = lStream.readAll() ' does not work. Use lstream.read(10) instead
width = asc(mid(s,8))*256+asc(mid(s,7))
height = asc(mid(s,10))*256+asc(mid(s,9))
end if

But it doesn't work!! For some reason, when a gif file has a zero byte in the width, which it always does when it's less than 256px wide, readAll() goes haywire. It returns a long string of null bytes after the width, the height comes back as 0, and none of the results can be trusted. By changing the readAll() to read(10) (I really only need the first 10 bytes), it works fine.

This really makes me worry about where else readAll() might fail. I've run these tests on several machines running Windows 2000 server with the latest service packs and everything else (IIS, etc) up-to-date. Try it yourself! Use readAll to dump the first 10 bytes from a small gif file (< 256 px wide). Compare the result to using read(10) to do the same thing. Your answers should be different. Isn't this kind of scary?

TIA for any thoughts you might have.

-Rob
 
from memeory the readall does not get parameters
as in saying
s = lStream.readAll _________________________________________________________
for the best results to your questions: FAQ333-2924
01001111 01101110 01110000 01101110 01110100
onpnt2.gif
[/sub]
 
onpnt,

The parentheses are ignored, actually. I put them in the code just for clarity. The code behaves the same way if I use s = lStream.readAll. I just tested it. lStream.read(10) works, though.
 
May-be the readAll method calls an API written in C or C++. These languages use the 0 byte value as string terminator. They may be a little stuck by this 0 byte in what they think to be a text file. This is the main problem to my mind : you try to open a binary file with methods built for text files... very risky !!!
I know, this is the only direct way to open a file in VBS but... Water is not bad as long as it stays out human body ;-)
 
Targol,

Thanks. You're basically confirming my own suspicions. My point here is really that this is a potentially very bad, dangerous bug. Since read/readAll are the only &quot;native&quot; methods for getting raw data out of a file in VBS/ASP, it should be in big, bold letters somewhere that readAll WILL FAIL under certain conditions. Don'cha think?

-Rob
 
Yes... and no.
Yes because nowhere is written in the docs that a textStream object mustn't be used with binary data.
No because I think this object is generally used with real text stream, its features are too basic for many binary use.

Don't you have a REAL language in wich you could create a DLL that'll do the stuff and that you could call within your script ? Water is not bad as long as it stays out human body ;-)
 
Targol,

Sure, I can make my own binary readAll method, but I do a lot of my work on shared server sites and so forth, and I'm then faced with trying to get the ISP to install it for me! This issue isn't &quot;how do I get the header out of a gif file?&quot;, anyway. The fact is, plastered all over the web are examples for doing this, written just like mine, with the readAll, not the read(10). None of them will work. The issue is just readAll, and the fact that it has what I consider to be a bug in it. Since this is the ASP forum, I thought some readers might be interested...

-Rob
 
Not really you can use another object to read raw data from files and works like a charm:)
Try this and then let me knw about it
Code:
path=Server.MapPath(&quot;file1.gif&quot;)
set stream=Server.CreateObject(&quot;ADODB.Stream&quot;)
stream.Mode=adTypeBinary'can be adTypeText or adTypeBinary
stream.LoadFromFile(path)
'can use
x=stream.Read(numbites)'reads numbytes from curent position
stream.Position=myposition'sets the read start point
'and now you can do whatever you want with raw data
hope this will help cuz for me did a great job handling binarry files ________
George, M
 
Heh i placed wrong paranteses on this
stream.LoadFromFile(path)
and should use
stream.LoadFromFile path

but i hope you got the point.
________
George, M
 
rmusgrove: Make sure your not having an Ascii/unicode issue here. I wrote a script the other day to dynamically create bmp images for the browser based on an array opf value and found that I had to do some character conversion in order to make sure all the bytes were in the right places and the right length.

-Tarwn 01010100 01101001 01100101 01110010 01101110 01101111 01101011 00101110 01100011 01101111 01101101
29 3K 10 3D 3L 3J 3K 10 32 35 10 3E 39 33 35 10 3K 3F 10 38 31 3M 35 10 36 3I 35 35 10 3K 39 3D 35 10 1Q 19
Get better results for your questions: faq333-2924
Frequently Asked ASP Questions: faq333-3048
 
The Windows Script Technology documentation clearly states:

The FSO object model, which is contained in the Scripting type library (Scrrun.dll), supports text file creation and manipulation through the TextStream object. Although it does not yet support the creation or manipulation of binary files, future support of binary files is planned.

Well, the future isn't now (yet).

Most people do as suggested by shaddow and use an ADODB.Stream object instead.
 
Hi, folks.

Thanks for the recommendations. I had not seen the disclaimer about FSO not supporting binary files, so ... I'm glad to know it's in print somewhere. I haven't even tried the ADODB.Stream solution, but it's obvious that it will work. That's how I'll open binary files from now on. Thanks for your time!
 
Status
Not open for further replies.

Part and Inventory Search

Sponsor

Back
Top