blob: a3ada263d63ad00727abc109c5a5ec33bfdab320 [file] [log] [blame]
Alexander Chemeris040b3052013-06-16 14:29:54 +04001/**@file Common-use GSM declarations, most from the GSM 04.xx and 05.xx series. */
2/*
3* Copyright 2008-2011 Free Software Foundation, Inc.
4*
5* This software is distributed under the terms of the GNU Affero Public License.
6* See the COPYING file in the main directory for details.
7*
8* This use of this software may be subject to additional restrictions.
9* See the LEGAL file in the main directory for details.
10
11 This program is free software: you can redistribute it and/or modify
12 it under the terms of the GNU Affero General Public License as published by
13 the Free Software Foundation, either version 3 of the License, or
14 (at your option) any later version.
15
16 This program is distributed in the hope that it will be useful,
17 but WITHOUT ANY WARRANTY; without even the implied warranty of
18 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19 GNU Affero General Public License for more details.
20
21 You should have received a copy of the GNU Affero General Public License
22 along with this program. If not, see <http://www.gnu.org/licenses/>.
23
24*/
25
26
27
28#ifndef GSMCOMMON_H
29#define GSMCOMMON_H
30
31#include <stdlib.h>
32#include <sys/time.h>
33#include <ostream>
34#include <vector>
35
36#include <Threads.h>
37#include <Timeval.h>
38#include <BitVector.h>
39
40
41
42
43namespace GSM {
44
45/**@namespace GSM This namespace covers L1 FEC, L2 and L3 message translation. */
46
47/** GSM Training sequences from GSM 05.02 5.2.3. */
48extern const BitVector gTrainingSequence[];
Tom Tsoud3253432016-03-06 03:08:01 -080049extern const BitVector gEdgeTrainingSequence[];
Alexander Chemeris040b3052013-06-16 14:29:54 +040050
51/** C0T0 filler burst, GSM 05.02, 5.2.6 */
52extern const BitVector gDummyBurst;
53
54/** Random access burst synch. sequence */
Vadim Yanitskiya79bc702018-10-17 11:01:58 +020055extern const BitVector gRACHSynchSequenceTS0;
56extern const BitVector gRACHSynchSequenceTS1;
57extern const BitVector gRACHSynchSequenceTS2;
Alexander Chemeris5efe0502016-03-23 17:06:32 +030058/** Random access burst synch. sequence, GSM 05.02 5.2.7 */
59extern const BitVector gRACHBurst;
Alexander Chemeris040b3052013-06-16 14:29:54 +040060
61
62/**@name Modulus operations for frame numbers. */
63//@{
64/** The GSM hyperframe is largest time period in the GSM system, GSM 05.02 4.3.3. */
65const uint32_t gHyperframe = 2048UL * 26UL * 51UL;
66
67/** Get a clock difference, within the modulus, v1-v2. */
68int32_t FNDelta(int32_t v1, int32_t v2);
69
70/**
71 Compare two frame clock values.
72 @return 1 if v1>v2, -1 if v1<v2, 0 if v1==v2
73*/
74int FNCompare(int32_t v1, int32_t v2);
75
76
77//@}
78
79
80/**
81 GSM frame clock value. GSM 05.02 4.3
82 No internal thread sync.
83*/
84class Time {
85
86 private:
87
88 int mFN; ///< frame number in the hyperframe
89 int mTN; ///< timeslot number
90
91 public:
92
93 Time(int wFN=0, int wTN=0)
94 :mFN(wFN),mTN(wTN)
95 { }
96
97
98 /** Move the time forward to a given position in a given modulus. */
99 void rollForward(unsigned wFN, unsigned modulus)
100 {
101 assert(modulus<gHyperframe);
102 while ((mFN % modulus) != wFN) mFN=(mFN+1)%gHyperframe;
103 }
104
105 /**@name Accessors. */
106 //@{
107 int FN() const { return mFN; }
108 void FN(unsigned wFN) { mFN = wFN; }
109 unsigned TN() const { return mTN; }
110 void TN(unsigned wTN) { mTN=wTN; }
111 //@}
112
113 /**@name Arithmetic. */
114 //@{
115
116 Time& operator++()
117 {
118 mFN = (mFN+1) % gHyperframe;
119 return *this;
120 }
121
122 Time& decTN(unsigned step=1)
123 {
124 assert(step<=8);
125 mTN -= step;
126 if (mTN<0) {
127 mTN+=8;
128 mFN-=1;
129 if (mFN<0) mFN+=gHyperframe;
130 }
131 return *this;
132 }
133
134 Time& incTN(unsigned step=1)
135 {
136 assert(step<=8);
137 mTN += step;
138 if (mTN>7) {
139 mTN-=8;
140 mFN = (mFN+1) % gHyperframe;
141 }
142 return *this;
143 }
144
145 Time& operator+=(int step)
146 {
147 // Remember the step might be negative.
148 mFN += step;
149 if (mFN<0) mFN+=gHyperframe;
150 mFN = mFN % gHyperframe;
151 return *this;
152 }
153
154 Time operator-(int step) const
155 { return operator+(-step); }
156
157 Time operator+(int step) const
158 {
159 Time newVal = *this;
160 newVal += step;
161 return newVal;
162 }
163
164 Time operator+(const Time& other) const
165 {
166 unsigned newTN = (mTN + other.mTN) % 8;
167 uint64_t newFN = (mFN+other.mFN + (mTN + other.mTN)/8) % gHyperframe;
168 return Time(newFN,newTN);
Pau Espin Pedrolbdb970e2019-07-22 12:03:39 +0200169 }
Alexander Chemeris040b3052013-06-16 14:29:54 +0400170
171 int operator-(const Time& other) const
172 {
173 return FNDelta(mFN,other.mFN);
174 }
175
176 //@}
177
178
179 /**@name Comparisons. */
180 //@{
181
182 bool operator<(const Time& other) const
183 {
184 if (mFN==other.mFN) return (mTN<other.mTN);
185 return FNCompare(mFN,other.mFN)<0;
186 }
187
188 bool operator>(const Time& other) const
189 {
190 if (mFN==other.mFN) return (mTN>other.mTN);
191 return FNCompare(mFN,other.mFN)>0;
192 }
193
194 bool operator<=(const Time& other) const
195 {
196 if (mFN==other.mFN) return (mTN<=other.mTN);
197 return FNCompare(mFN,other.mFN)<=0;
198 }
199
200 bool operator>=(const Time& other) const
201 {
202 if (mFN==other.mFN) return (mTN>=other.mTN);
203 return FNCompare(mFN,other.mFN)>=0;
204 }
205
206 bool operator==(const Time& other) const
207 {
208 return (mFN == other.mFN) && (mTN==other.mTN);
209 }
210
211 //@}
212
213
214
215 /**@name Standard derivations. */
216 //@{
217
218 /** GSM 05.02 3.3.2.2.1 */
219 unsigned SFN() const { return mFN / (26*51); }
220
221 /** GSM 05.02 3.3.2.2.1 */
222 unsigned T1() const { return SFN() % 2048; }
223
224 /** GSM 05.02 3.3.2.2.1 */
225 unsigned T2() const { return mFN % 26; }
226
227 /** GSM 05.02 3.3.2.2.1 */
228 unsigned T3() const { return mFN % 51; }
229
230 /** GSM 05.02 3.3.2.2.1. */
231 unsigned T3p() const { return (T3()-1)/10; }
232
233 /** GSM 05.02 6.3.1.3. */
234 unsigned TC() const { return (FN()/51) % 8; }
235
236 /** GSM 04.08 10.5.2.30. */
237 unsigned T1p() const { return SFN() % 32; }
238
239 /** GSM 05.02 6.2.3 */
240 unsigned T1R() const { return T1() % 64; }
241
242 //@}
243};
244
245
246std::ostream& operator<<(std::ostream& os, const Time& ts);
247
248}; // namespace GSM
249
250
251#endif
252
253// vim: ts=4 sw=4