function jhc(s) {
	return s
		.replace(/&/g, '&amp;')
		.replace(/</g, '&lt;')
		.replace(/"/g, '&quot;');
}

function jcc(ftxt) { // function compiler
	if (!(/return\W*$/.test(ftxt))) {
		ftxt = ftxt.replace(/(\w+)(\W*)$/, 'return $1$2');
	}
	var f;
	eval('f = function(a) { ' + ftxt + '}');
	return f;
}

function jst(s, f) { // performs at roughly 281 ms / 1000 transforms
	var r=0, p=0, e=0;
	var index = [];
	while ((p=s.indexOf('<%', r)) != -1) {
		if ((e=s.indexOf('%>', p+2)) != -1) {
			index[index.length] = s.substring(r, p);
			// index[index.length] = s.substring(p+2, e);
			index[index.length] = jcc(s.substring(p+2, e));
			r = e + 2;
		} else break;
	}
	s = s.substring(r);
	var u = function(a) {
		var o='', i;
		function write(s) { o += s }
		for (i=0; i<index.length; i+=2)
//			o += index[i] + (f
//				? f(eval(index[i+1]))
//				:   eval(index[i+1])
//			);
			o += index[i] + (f
				? f(index[i+1](a))
				:   index[i+1](a)
			);
		return o + s;
	};
	return u;
}

