Download Reference Manual
The Developer's Library for D
About Wiki Forums Source Search Contact

MemoryFile

Moderators: kris

Posted: 02/28/09 18:36:23

Here is a memory file class. It emulates the behavior of a file. I.e. you can seek beyond the buffer size. Could be used as replacement of TempFile? or FileConduit? without code changes. I don't know if it works with the latest trunk. If it doesn't, then it will need minor changes to use the latest io stuff.

Regards, bobef

import tango.io.device.Conduit;
import tango.io.model.IConduit;
import tango.stdc.stdlib;
import tango.stdc.string;

class MemoryFile : Conduit, IConduit.Seek {
	this(uint initialsize = 0) {
		if(initialsize > 0) resize(initialsize);
	}

	~this() {
		if(mbuffer) detach();
	}

	uint bufferSize() {
		return 4096;
	}

	char[] toString() {
		return "MemoryFile";
	}

	long seek(long offset, Anchor anchor = Anchor.Begin) {
		if(anchor == Anchor.Begin) mposition = offset;
		else if(anchor == Anchor.Current) mposition += offset;
		else mposition = mlength + offset;
		return mposition;
	}

	void detach() {
		mlength = 0;
		mposition = 0;
		if(mbuffer) {
			free(mbuffer);
			mbuffer = null;
		}
	}

	size_t read(void[] dst) {
		if(mposition >= mlength) return 0;
		else {
			auto end = mposition+dst.length>mlength ? mlength-mposition : dst.length;
			auto tpos = mposition+end;
			dst[0..end] = mbuffer[mposition..tpos];
			mposition = tpos;
			return end;
		}
	}

	size_t write(void[] src) {
		auto tsize = mposition+src.length; 
		auto oldsize = mlength;
		if(tsize > mlength) resize(tsize);
		if(mposition > oldsize) memset(mbuffer+oldsize,0,mposition-oldsize);
		mbuffer[mposition..tsize] = src;
		mposition = tsize;
		return src.length;
	}

	long length() {
		return mlength;
	}

	long position() {
		return mposition;
	}

protected:
	void* mbuffer;
	size_t mlength;
	long mposition;

	void resize(uint len) {
		mbuffer = realloc(mbuffer,len);
		if(mbuffer) mlength = len;
		else throw new tango.core.Exception.OutOfMemoryException(__FILE__,__LINE__);
	}
}
Author Message

Posted: 03/01/09 02:46:30

I believe tango.io.device.Array fills this need already...

The latest trunk has vast changes to tango.io.

Posted: 03/01/09 09:18:55

The docs of device.io.Array.seek says "Seek within the constraints of assigned content". In a file you can seek anywhere, so you can't drop this array in code that works with files.

Posted: 03/01/09 12:05:57

bobef wrote:

The docs of device.io.Array.seek says "Seek within the constraints of assigned content". In a file you can seek anywhere, so you can't drop this array in code that works with files.

I don't see how that is different from files? You can't seek outside of the data in the file either.

Posted: 03/01/09 14:20:40

Yes, you can. You can seek beyond the end of the file and when you write something, it will be written at this position.