z_mirror/hare-fmm

git clone https://git.raiguard.me/z_mirror/hare-fmm

Caleb HeuerGet main program working on modern Hare88c1a72

trunk
2.0 KiB70 linesraw
1use fmt;
2use strconv;
3use strings;
4
5// A [[version]] has four components, being major, minor, patch, and build.
6// Build is only used for internal game mechanics, and is not usable by mods.
7type version = [4]u16;
8
9// Any error which may be returned by a version function.
10type version_error = !(strconv::error | version_invalid_len);
11
12// Indicates that the version string has too many or too few parts. Contains
13// the number of parts received.
14type version_invalid_len = !size;
15
16// Indicates the result of comparing two [[version]]s. Also contains some extra
17// variants for dependency validation.
18//
19// The value is encoded in binary as '(eq)(lt)(gt)'.
20type version_cmpres = enum u8 {
21	ANY = 0,
22	EQ,
23	GT,
24	GTEQ,
25	LT,
26	LTEQ = 6,
27};
28
29// Compares two [[version]]s for equality.
30fn version_cmp(v1: version, v2: version) version_cmpres = {
31	for (let i = 0z; i < len(v1); i += 1) {
32		if (v1[i] > v2[i]) {
33			return version_cmpres::GT;
34		} else if (v1[i] < v2[i]) {
35			return version_cmpres::LT;
36		};
37	};
38	return version_cmpres::EQ;
39};
40
41// Parses a [[version]] from an input string.
42fn version_parse(input: str) (version | version_error) = {
43	let parts = strings::split(strings::trim(input), ".")!;
44	if (len(parts) < 2 || len(parts) > 4)
45		return len(parts): version_invalid_len;
46	let version: version = [0...];
47	for (let i = 0z; i < len(parts); i += 1)
48		version[i] = strconv::stou16(parts[i])?;
49	return version;
50};
51
52// Formats a [[version]] for printing. The return value must be freed by the
53// caller.
54fn version_str(ver: version, include_build: bool) str = {
55	if (include_build) {
56		return fmt::asprintf("{}.{}.{}.{}", ver[0], ver[1], ver[2], ver[3])!;
57	} else {
58		return fmt::asprintf("{}.{}.{}", ver[0], ver[1], ver[2])!;
59	};
60};
61
62// Converts a [[version_error]] into a user-friendly string.
63fn version_strerror(err: version_error) str = {
64	match (err) {
65	case version_invalid_len =>
66		return "Invalid number of version parts";
67	case let err: strconv::error =>
68		return strconv::strerror(err);
69	};
70};