vio/vio.lua

Fri, 05 May 2017 09:47:52 +0100

author
Matthew Wild <mwild1@gmail.com>
date
Fri, 05 May 2017 09:47:52 +0100
branch
lua5.2
changeset 95
828e814152e0
parent 19
f72a0f535301
permissions
-rw-r--r--

squish: Optionally add in a 5.2-compatible module() function (5.2's own compat function is broken)

--module-compat or --no-module-compat, default is --module-compat if running under 5.2+ (detected at runtime).

When compiled with the appropriate flags, Lua 5.2 provides a module() function for backwards compatibility with
5.1. However 5.1's version of the function changed function environments, while 5.2's version changes the global
environment, which breaks through squish's per-module sandbox functions.

local vio = {};
vio.__index = vio; 
	
function vio.open(string)
	return setmetatable({ pos = 1, data = string }, vio);
end

function vio:read(format, ...)
	if self.pos >= #self.data then return; end
	if format == "*a" then
		local oldpos = self.pos;
		self.pos = #self.data;
		return self.data:sub(oldpos, self.pos);
	elseif format == "*l" then
		local data;
		data, self.pos = self.data:match("([^\r\n]*)\r?\n?()", self.pos)
		return data;
	elseif format == "*n" then
		local data;
		data, self.pos = self.data:match("(%d+)()", self.pos)
		return tonumber(data);	
	elseif type(format) == "number" then
		local oldpos = self.pos;
		self.pos = self.pos + format;
		return self.data:sub(oldpos, self.pos-1);
	end
end

function vio:seek(whence, offset)
	if type(whence) == "number" then
		whence, offset = "cur", whence;
	end
	offset = offset or 0;
	
	if whence == "cur" then
		self.pos = self.pos + offset;
	elseif whence == "set" then
		self.pos = offset + 1;
	elseif whence == "end" then
		self.pos = #self.data - offset;
	end
	
	return self.pos;
end

local function _readline(f) return f:read("*l"); end
function vio:lines()
	return _readline, self;
end

function vio:write(...)
	for i=1,select('#', ...) do
		local dat = tostring(select(i, ...));
		self.data = self.data:sub(1, self.pos-1)..dat..self.data:sub(self.pos+#dat, -1);
	end
end

function vio:close()
	self.pos, self.data = nil, nil;
end

mercurial