0

I have some code that uses ReadStr and WriteStr for what I presume is writing a string to a binary file.

The explanation for WriteStr in the documentation states that it will write raw data in the shape of an AnsiString to the object's stream, which makes sense. But then ReadStr says that it reads a character. So are they not the opposite of each other?

Let say I have,

pName: String[80];

and I use WriteStr on it, what does it actually write? Since WriteStr expects AnsiString, does it cast pName to be such? In that case, does it not write the "Length" field into the stream because an AnsiString pointer points to the first element and not the length field? I was also looking and it seems String == AnsiString these days, but my question about the length field still remains the same.

If lets say it doesn't write the Length field into the file, does it still write the NULL at the end of the data? As such, can I find where the string ends by looking for a '\0'? Does ReadStr read until the NULL character?

Thank you kindly :)

Mewa
  • 502
  • 1
  • 9
  • 24
  • Very hard to say what these functions do. Perhaps if you showed the code for them we might have more chance. – David Heffernan Jun 19 '13 at 06:02
  • 2
    Is it the [`TWriter.WriteStr`](http://docwiki.embarcadero.com/Libraries/XE4/en/System.Classes.TWriter.WriteStr) and [`TReader.ReadStr`](http://docwiki.embarcadero.com/Libraries/XE2/en/System.Classes.TReader.ReadStr)? They are marked as for internal use only. – LU RD Jun 19 '13 at 06:07
  • @DavidHeffernan, they're as LU RD mentioned actually TReader.ReadStr and TWriter.WriteStr. I have no code for these functions as they are built in and only short snippets are available to explain their purpose. – Mewa Jun 19 '13 at 06:28
  • @LURD, I am not the one who used these functions, but I need to figure out what the code does. So while I read that they're for internal use only, it seems these guys used them anyways :/ – Mewa Jun 19 '13 at 06:28
  • Don't you have the Delphi RTL source? – David Heffernan Jun 19 '13 at 06:35
  • Don't make us guess, please. [`ReadStr`](http://www.freepascal.org/docs-html/rtl/system/readstr.html)? [`ReadStr`](http://docwiki.embarcadero.com/Libraries/XE4/en/System.Classes.TReader.ReadStr)? – OnTheFly Jun 19 '13 at 11:42
  • @user539484 Well, I expect we can rule out the one that is not part of Delphi – David Heffernan Jun 19 '13 at 12:01
  • @user539484, I figured the "Delphi" in the title would have sufficed to explain that it isn't the Pascal one. – Mewa Jun 19 '13 at 15:17
  • Why the downvote? This looks like a valid question. – Leonardo Herrera Jun 19 '13 at 17:21

1 Answers1

3

In your pre-Unicode version of Delphi, WriteStr and ReadStr write and read an AnsiString value. The writing code writes the length, and then the string content. The reading code reads the length, allocates the string, and then fills it with the content.

This has the potential of involving a truncation when you assign the result of ReadStr to your 80 character short string.

David Heffernan
  • 601,492
  • 42
  • 1,072
  • 1,490
  • Thank you! So the length field is still there, that is good to know. What about the rest of the fields? _"The AnsiString structure contains a 32-bit length indicator, a 32-bit reference count, a 16-bit data length indicating the number of bytes per character, and a 16-bit code page."_ From this description it seems like more information should be written, or is it just omitted? – Mewa Jun 19 '13 at 15:12
  • That information doesn't need to be written, and some of it is not even present in your pre Unicode Delphi. For example the reference count has no meaning in the file, only in memory. – David Heffernan Jun 19 '13 at 15:30
  • Alright, that makes sense, thanks! I think I can take it from here :) – Mewa Jun 19 '13 at 17:34