File: InfoErrors.cpp

package info (click to toggle)
storm-lang 0.7.4-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid
  • size: 52,004 kB
  • sloc: ansic: 261,462; cpp: 140,405; sh: 14,891; perl: 9,846; python: 2,525; lisp: 2,504; asm: 860; makefile: 678; pascal: 70; java: 52; xml: 37; awk: 12
file content (127 lines) | stat: -rw-r--r-- 2,896 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
#include "stdafx.h"
#include "InfoErrors.h"
#include "InfoNode.h"

namespace storm {
	namespace syntax {

		static const Nat failedMask  = 0x80000000;
		static const Nat shiftsMask  = 0x7FFF0000;
		static const Nat charsMask   = 0x0000FFFF;
		static const Nat shiftsShift = 16;

		InfoErrors::InfoErrors() : data(0) {}

		InfoErrors::InfoErrors(Nat data) : data(data) {}

		Bool InfoErrors::success() const {
			return (data & failedMask) == 0;
		}

		Bool InfoErrors::any() const {
			// Checks: success() == false || shifts() > 0 || chars() > 0
			return data != 0;
		}

		Nat InfoErrors::shifts() const {
			return (data & shiftsMask) >> shiftsShift;
		}

		Nat InfoErrors::chars() const {
			return data & charsMask;
		}

		void InfoErrors::chars(Nat chars) {
			data &= ~charsMask;
			data |= min(chars, charsMask);
		}

		InfoErrors InfoErrors::operator +(InfoErrors e) const {
			Nat f = (data & failedMask) | (e.data & failedMask);
			Nat a = min(shifts() + e.shifts(), shiftsMask >> shiftsShift);
			Nat b = min(chars() + e.chars(), charsMask);

			return InfoErrors(f | (a << shiftsShift) | b);
		}

		InfoErrors &InfoErrors::operator +=(InfoErrors e) {
			// We're just an int, so this is fairly reasonable.
			*this = *this + e;
			return *this;
		}

		static inline Nat value(InfoErrors e) {
			if (!e.success())
				return failedMask;
			else
				return e.shifts() + e.chars();
		}

		Bool InfoErrors::operator <(InfoErrors e) const {
			return value(*this) < value(e);
		}

		Bool InfoErrors::operator ==(InfoErrors e) const {
			return value(*this) == value(e);
		}

		Bool InfoErrors::operator !=(InfoErrors e) const {
			return value(*this) != value(e);
		}

		InfoErrors infoFailure() {
			return InfoErrors(failedMask);
		}

		InfoErrors infoSuccess() {
			return InfoErrors(0);
		}

		InfoErrors infoShifts(Nat shifts) {
			shifts = min(shifts, shiftsMask >> shiftsShift);
			return InfoErrors((shifts << shiftsShift) & shiftsMask);
		}

		InfoErrors infoChars(Nat chars) {
			chars = min(chars, charsMask);
			return InfoErrors(chars & charsMask);
		}

		Nat InfoErrors::getData(InfoErrors e) {
			return e.data;
		}

		InfoErrors InfoErrors::fromData(Nat v) {
			return InfoErrors(v);
		}

		void InfoErrors::toS(StrBuf *to) const {
			if (success()) {
				if (!any()) {
					*to << S("success");
				} else {
					*to << chars() << (chars() == 1 ? S(" char") : S(" chars")) << L", ";
					*to << shifts() << (shifts() == 1 ? S(" correction") : S(" corrections"));
				}
			} else {
				*to << S("failure");
			}
		}

		wostream &operator <<(wostream &to, InfoErrors e) {
			if (e.success()) {
				if (!e.any()) {
					to << L"success";
				} else {
					to << e.chars() << (e.chars() == 1 ? L" char" : L" chars") << L", ";
					to << e.shifts() << (e.shifts() == 1 ? L" correction" : L" corrections");
				}
			} else {
				to << L"failure";
			}

			return to;
		}

	}
}