shithub: mc

Download patch

ref: a74746cf0a22bd451ae9a57f350cbf1c0d7fd3f9
parent: 6f893e4ef65b27ec2241b8375a465bbf41e3622b
author: Ori Bernstein <[email protected]>
date: Mon Aug 26 22:57:14 EDT 2013

Add zoneinfo parser. Not part of build yet.

--- /dev/null
+++ b/libstd/zoneinfo.myr
@@ -1,0 +1,124 @@
+use "alloc.use"
+use "die.use"
+use "sleq.use"
+use "slurp.use"
+use "sys.use"
+use "types.use"
+use "fmt.use"
+
+pkg _timezone =
+	type zifile
+	const load	: (file : byte[:] -> zifile#)
+;;
+
+type zifile = struct
+	time	: int32[:]
+	timetype: byte[:]
+	ttinfo 	: ttinfo[:]
+	abbrev	: byte[:]
+	leap	: int32[2][:]
+	isstd	: byte[:]
+	isgmt	: byte[:]
+;;
+
+type ttinfo = struct
+	gmtoff	: int32
+	isdst	: byte
+	abbrind	: byte
+;;
+
+const load = {file
+	var nisgmt
+	var nisstd
+	var nleap
+	var ntime
+	var ntype
+	var nchar
+	var i
+	var f
+	var p
+
+	/* check magic */
+	p = std.slurp(file)
+	if !std.sleq(p[:4], "TZif")
+		-> 0 castto(zifile#)
+	;;
+
+	/* skip to data */
+	p = p[20:]
+	(nisgmt, p) = fetchbe32(p)
+	(nisstd, p) = fetchbe32(p)
+	(nleap, p) = fetchbe32(p)
+	(ntime, p) = fetchbe32(p)
+	(ntype, p) = fetchbe32(p)
+	(nchar, p) = fetchbe32(p)
+
+
+	f = std.alloc()
+	f.time = std.slalloc(ntime castto(std.size))
+	for i = 0; i < ntime; i++
+		(f.time[i], p) = fetchbe32(p)
+	;;
+
+	f.timetype = std.slalloc(ntime castto(std.size))
+	for i = 0; i < ntime; i++
+		(f.timetype[i], p) = fetchbe8(p)
+	;;
+
+	f.ttinfo = std.slalloc(ntype castto(std.size))
+	for i = 0; i < ntype; i++
+		p = fetchttinfo(p, &f.ttinfo[i])
+	;;
+
+	f.abbrev = std.slalloc(nchar castto(std.size))
+	for i = 0; i < nchar; i++
+		(f.abbrev[i], p) = fetchbe8(p)
+	;;
+
+	f.leap = std.slalloc(nleap castto(std.size))
+	for i = 0; i < nleap; i++
+		(f.leap[i][0], p) = fetchbe32(p)
+		(f.leap[i][1], p) = fetchbe32(p)
+	;;
+
+	f.isstd = std.slalloc(nisstd castto(std.size))
+	for i = 0; i < nisstd; i++
+		(f.isstd[i], p) = fetchbe8(p)
+	;;
+
+	f.isgmt = std.slalloc(nisgmt castto(std.size))
+	for i = 0; i < nisgmt; i++
+		(f.isgmt[i], p) = fetchbe8(p)
+	;;
+
+
+	-> f
+}
+
+const fetchbe32 = {sl
+	var v
+
+	std.assert(sl.len >= 4, "Slice too small to fetch int32 from")
+	v = 	(sl[0] castto(int32)) << 24 | \
+		(sl[1] castto(int32)) << 16 | \
+		(sl[2] castto(int32)) << 8  | \
+		(sl[3] castto(int32)) << 0  
+	-> (v, sl[4:])
+}
+
+const fetchbe8 = {sl
+	var v
+
+	std.assert(sl.len >= 1, "Slice too small to fetch int8 from")
+	v = sl[0]
+	-> (v, sl[1:])
+}
+
+
+const fetchttinfo = {sl, dst : ttinfo#
+	(dst.gmtoff, sl) = fetchbe32(sl)
+	(dst.isdst, sl) = fetchbe8(sl)
+	(dst.abbrind, sl) = fetchbe8(sl)
+	-> sl
+}
+