Subversion Repositories Projects

Rev

Rev 1568 | Rev 1601 | Go to most recent revision | Only display areas with differences | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 1568 Rev 1573
1
package dongfang.mkt.comm;
1
package dongfang.mkt.comm;
2
 
2
 
3
import java.io.IOException;
3
import java.io.IOException;
4
import java.io.InputStream;
4
import java.io.InputStream;
5
import java.io.OutputStream;
5
import java.io.OutputStream;
6
 
6
 
7
import dongfang.mkt.datatype.GPSBearingAndRange;
7
import dongfang.mkt.datatype.GPSBearingAndRange;
8
import dongfang.mkt.datatype.GPSPosition;
8
import dongfang.mkt.datatype.GPSPosition;
9
import dongfang.mkt.frames.AllDisplaysResponseFrame;
9
import dongfang.mkt.frames.AllDisplaysResponseFrame;
10
import dongfang.mkt.frames.AnalogDebugLabelResponseFrame;
10
import dongfang.mkt.frames.AnalogDebugLabelResponseFrame;
11
import dongfang.mkt.frames.AttitudeDataResponseFrame;
11
import dongfang.mkt.frames.AttitudeDataResponseFrame;
12
import dongfang.mkt.frames.ChangeParameterSetResponseFrame;
12
import dongfang.mkt.frames.ChangeParameterSetResponseFrame;
13
import dongfang.mkt.frames.CompassHeadingResponseFrame;
13
import dongfang.mkt.frames.CompassHeadingResponseFrame;
14
import dongfang.mkt.frames.ConfirmFrame;
14
import dongfang.mkt.frames.ConfirmFrame;
15
import dongfang.mkt.frames.DebugResponseFrame;
15
import dongfang.mkt.frames.DebugResponseFrame;
16
import dongfang.mkt.frames.MotorTestResponseFrame;
16
import dongfang.mkt.frames.MotorTestResponseFrame;
17
import dongfang.mkt.frames.OSDDataResponseFrame;
17
import dongfang.mkt.frames.OSDDataResponseFrame;
18
import dongfang.mkt.frames.ReadExternalControlResponseFrame;
18
import dongfang.mkt.frames.ReadExternalControlResponseFrame;
19
import dongfang.mkt.frames.ResponseFrame;
19
import dongfang.mkt.frames.ResponseFrame;
20
import dongfang.mkt.frames.SetCompassHeadingResponseFrame;
20
import dongfang.mkt.frames.SetCompassHeadingResponseFrame;
21
import dongfang.mkt.frames.UniversalReadParamSetResponseFrame;
21
import dongfang.mkt.frames.UniversalReadParamSetResponseFrame;
22
import dongfang.mkt.frames.UniversalWriteParamSetResponseFrame;
22
import dongfang.mkt.frames.UniversalWriteParamSetResponseFrame;
23
import dongfang.mkt.frames.VariablesResponseFrame;
23
import dongfang.mkt.frames.VariablesResponseFrame;
24
import dongfang.mkt.frames.VersionResponseFrame;
24
import dongfang.mkt.frames.VersionResponseFrame;
25
 
25
 
26
public class MKInputStream extends InputStream {
26
public class MKInputStream extends InputStream {
27
        int readByteCnt;
27
        int readByteCnt;
28
        class MKDataInputStream {
28
        class MKDataInputStream {
29
                int[] inbuf = new int[4];
29
                int[] inbuf = new int[4];
30
                int[] outbuf = new int[3];
30
                int[] outbuf = new int[3];
31
                int outbufptr = outbuf.length; // reset to "buffer empty"
31
                int outbufptr = outbuf.length; // reset to "buffer empty"
32
 
32
 
33
                private boolean decode() throws IOException {
33
                private boolean decode() throws IOException {
34
                        for (int i = 0; i < 4; i++) {
34
                        for (int i = 0; i < 4; i++) {
35
                                int raw = MKInputStream.this.readByte();
35
                                int raw = MKInputStream.this.readByte();
36
                                int in = raw - '=';
36
                                int in = raw - '=';
37
                                if (in < 0 || in > 63)
37
                                if (in < 0 || in > 63)
38
                                        return false;
38
                                        return false;
39
                                        // throw new IOException("Out of range data received where frame data expected. Probably the frame was shorter than expected (" + readByteCnt + ")!");
39
                                        // throw new IOException("Out of range data received where frame data expected. Probably the frame was shorter than expected (" + readByteCnt + ")!");
40
                                inbuf[i] = in;
40
                                inbuf[i] = in;
41
                                readByteCnt++;
41
                                readByteCnt++;
42
                        }
42
                        }
43
                        outbuf[0] = (inbuf[0] << 2) | (inbuf[1] >>> 4);
43
                        outbuf[0] = (inbuf[0] << 2) | (inbuf[1] >>> 4);
44
                        outbuf[1] = ((inbuf[1] & 0x0f) << 4) | (inbuf[2] >>> 2);
44
                        outbuf[1] = ((inbuf[1] & 0x0f) << 4) | (inbuf[2] >>> 2);
45
                        outbuf[2] = ((inbuf[2] & 0x03) << 6) | inbuf[3];
45
                        outbuf[2] = ((inbuf[2] & 0x03) << 6) | inbuf[3];
46
                        outbufptr = 0;
46
                        outbufptr = 0;
47
                        return true;
47
                        return true;
48
                }
48
                }
49
 
49
 
50
                public void reset() {
50
                public void reset() {
51
                        outbufptr = outbuf.length; // reset to "buffer empty"
51
                        outbufptr = outbuf.length; // reset to "buffer empty"
52
                }
52
                }
53
 
53
 
54
                public int readByte() throws IOException {
54
                public int readByte() throws IOException {
55
                        if (outbufptr > 2 && !decode())
55
                        if (outbufptr > 2 && !decode())
56
                                        throw new IOException("Out of range data received where frame data expected. Probably the frame was shorter than expected (" + readByteCnt + ")!");            
56
                                        throw new IOException("Out of range data received where frame data expected. Probably the frame was shorter than expected (" + readByteCnt + ")!");            
57
                        return outbuf[outbufptr++];
57
                        return outbuf[outbufptr++];
58
                }
58
                }
59
 
59
 
60
                public int readSignedByte() throws IOException {
60
                public int readSignedByte() throws IOException {
61
                        byte result = (byte)readByte();
61
                        byte result = (byte)readByte();
62
                        return result;
62
                        return result;
63
                }
63
                }
64
 
64
 
65
                public int readWord() throws IOException {
65
                public int readWord() throws IOException {
66
                        int byte0 = readByte();
66
                        int byte0 = readByte();
67
                        int byte1 = readByte();
67
                        int byte1 = readByte();
68
                        return (byte1 << 8) | byte0;
68
                        return (byte1 << 8) | byte0;
69
                }
69
                }
70
 
70
 
71
                public int readSignedWord() throws IOException {
71
                public int readSignedWord() throws IOException {
72
                        int word = readWord();
72
                        int word = readWord();
73
                        if (word > 32767)
73
                        if (word > 32767)
74
                                word = word - 65536;
74
                                word = word - 65536;
75
                        return word;
75
                        return word;
76
                }
76
                }
77
               
77
               
78
                public int readSignedDWord() throws IOException {
78
                public int readSignedDWord() throws IOException {
79
                        int byte0 = readByte();
79
                        int byte0 = readByte();
80
                        int byte1 = readByte();
80
                        int byte1 = readByte();
81
                        int byte2 = readByte();
81
                        int byte2 = readByte();
82
                        int byte3 = readByte();
82
                        int byte3 = readByte();
83
                        return (byte3 << 24) | (byte2 << 16) | (byte1 << 8) | byte0;
83
                        return (byte3 << 24) | (byte2 << 16) | (byte1 << 8) | byte0;
84
                }
84
                }
85
 
85
 
86
                public int[] readBytes(int length) throws IOException {
86
                public int[] readBytes(int length) throws IOException {
87
                        int[] result = new int[length];
87
                        int[] result = new int[length];
88
                        for (int i = 0; i < length; i++) {
88
                        for (int i = 0; i < length; i++) {
89
                                result[i] = readByte();
89
                                result[i] = readByte();
90
                        }
90
                        }
91
                        return result;
91
                        return result;
92
                }
92
                }
93
 
93
 
94
                public int[] readWords(int length) throws IOException {
94
                public int[] readWords(int length) throws IOException {
95
                        int[] result = new int[length];
95
                        int[] result = new int[length];
96
                        for (int i = 0; i < length; i++) {
96
                        for (int i = 0; i < length; i++) {
97
                                result[i] = readWord();
97
                                result[i] = readWord();
98
                        }
98
                        }
99
                        return result;
99
                        return result;
100
                }
100
                }
101
 
101
 
102
                public int[] readSignedWords(int length) throws IOException {
102
                public int[] readSignedWords(int length) throws IOException {
103
                        int[] result = new int[length];
103
                        int[] result = new int[length];
104
                        for (int i = 0; i < length; i++) {
104
                        for (int i = 0; i < length; i++) {
105
                                result[i] = readSignedWord();
105
                                result[i] = readSignedWord();
106
                        }
106
                        }
107
                        return result;
107
                        return result;
108
                }
108
                }
109
 
109
 
110
                public char[] readChars(int length) throws IOException {
110
                public char[] readChars(int length) throws IOException {
111
                        char[] result = new char[length];
111
                        char[] result = new char[length];
112
                        for (int i = 0; i < length; i++) {
112
                        for (int i = 0; i < length; i++) {
113
                                // Here, a 1:1 mapping between byte values and char codes is assumed.
113
                                // Here, a 1:1 mapping between byte values and char codes is assumed.
114
                                // That means we're assuming ISO-8859-1 (= the first 256 code points
114
                                // That means we're assuming ISO-8859-1 (= the first 256 code points
115
                                // of Unicode, which Java uses for chars)
115
                                // of Unicode, which Java uses for chars)
116
                                result[i] = (char) readByte();
116
                                result[i] = (char) readByte();
117
                        }
117
                        }
118
                        return result;
118
                        return result;
119
                }
119
                }
120
        }
120
        }
121
 
121
 
122
        MKDataInputStream base64InputStream = new MKDataInputStream();
122
        MKDataInputStream base64InputStream = new MKDataInputStream();
123
        OutputStream nonPacketSpillway = null; //System.err;
123
        OutputStream nonPacketSpillway = null; //System.err;
124
       
124
       
125
        final InputStream is;
125
        final InputStream is;
126
        int crc;
126
        int crc;
127
 
127
 
128
        public MKInputStream(InputStream is) {
128
        public MKInputStream(InputStream is) {
129
                this.is = is;
129
                this.is = is;
130
        }
130
        }
131
       
131
       
132
        @Override
132
        @Override
133
        public int read() throws IOException {
133
        public int read() throws IOException {
134
                int i;
134
                int i;
135
                while ((i=is.read()) == -1);
135
                while ((i=is.read()) == -1);
136
                // System.out.print("Received: " + i + " (as char: " + (char)i + ")\n");
136
                // System.out.print("Received: " + i + " (as char: " + (char)i + ")\n");
137
                return i;
137
                return i;
138
        }
138
        }
139
 
139
 
140
        public int readByte() throws IOException {
140
        public int readByte() throws IOException {
141
                int _byte = read();
141
                int _byte = read();
142
                if (_byte < 0)
142
                if (_byte < 0)
143
                        throw new IOException("End of Stream!");
143
                        throw new IOException("End of Stream!");
144
                crc += _byte;
144
                crc += _byte;
145
                return _byte;
145
                return _byte;
146
        }
146
        }
147
 
147
 
148
        public MKDataInputStream getBase64InputStream() {
148
        public MKDataInputStream getBase64InputStream() {
149
                return base64InputStream;
149
                return base64InputStream;
150
        }
150
        }
151
 
151
 
152
        public ResponseFrame getNextFrame() throws IOException {
152
        public ResponseFrame getNextFrame() throws IOException {
153
                int c;
153
                int c;
154
                while ((c = read()) != '#') {
154
                while ((c = read()) != '#') {
155
                        // throw it on some scrap-text buffer.
155
                        // throw it on some scrap-text buffer.
156
                        if (nonPacketSpillway != null)
156
                        if (nonPacketSpillway != null)
157
                                nonPacketSpillway.write(c);
157
                                nonPacketSpillway.write(c);
158
                }
158
                }
159
                crc = '#';
159
                crc = '#';
160
                base64InputStream.reset();
160
                base64InputStream.reset();
161
                int address = readByte() - 'a';
161
                int address = readByte() - 'a';
162
                int iid = readByte();
162
                int iid = readByte();
163
                readByteCnt = 0;
163
                readByteCnt = 0;
164
                //RESPONSE_IDS id = getResponseType(iid);
164
                //RESPONSE_IDS id = getResponseType(iid);
165
                ResponseFrame result;
165
                ResponseFrame result;
166
//              System.out.println("Received a: " + (char)iid + " from " + address);
166
//              System.out.println("Received a: " + (char)iid + " from " + address);
167
                switch (iid) {
167
                switch (iid) {
168
                case 'A': {
168
                case 'A': {
169
                        AnalogDebugLabelResponseFrame f = new AnalogDebugLabelResponseFrame(address);
169
                        AnalogDebugLabelResponseFrame f = new AnalogDebugLabelResponseFrame(address);
170
                        f.setChannel(base64InputStream.readByte());
170
                        f.setChannel(base64InputStream.readByte());
171
                        f.setLabel(base64InputStream.readChars(16));
171
                        f.setLabel(base64InputStream.readChars(16));
172
                        result = f;
172
                        result = f;
173
                        break;
173
                        break;
174
                }
174
                }
175
                case 'B': {
175
                case 'B': {
176
                        ConfirmFrame f = new ConfirmFrame(address);
176
                        ConfirmFrame f = new ConfirmFrame(address);
177
                        f.setFrameNum(base64InputStream.readByte());
177
                        f.setFrameNum(base64InputStream.readByte());
178
                        result = f;
178
                        result = f;
179
                        break;
179
                        break;
180
                }
180
                }
181
                case 'C': {
181
                case 'C': {
182
                        AttitudeDataResponseFrame f = new AttitudeDataResponseFrame(address);
182
                        AttitudeDataResponseFrame f = new AttitudeDataResponseFrame(address);
183
                        f.setPitch(base64InputStream.readSignedWord());
183
                        f.setPitch(base64InputStream.readSignedWord());
184
                        f.setRoll(base64InputStream.readSignedWord());
184
                        f.setRoll(base64InputStream.readSignedWord());
185
                        f.setHeading(base64InputStream.readSignedWord());
185
                        f.setHeading(base64InputStream.readSignedWord());
186
                        f.setExpansion(base64InputStream.readBytes(8));
186
                        f.setExpansion(base64InputStream.readBytes(8));
187
                        result = f;
187
                        result = f;
188
                        break;
188
                        break;
189
                }
189
                }
190
                case 'D': {
190
                case 'D': {
191
                        DebugResponseFrame f = new DebugResponseFrame(address);
191
                        DebugResponseFrame f = new DebugResponseFrame(address);
192
                        for (int i=0; i<2; i++)
192
                        for (int i=0; i<2; i++)
193
                                f.setDigital(i, base64InputStream.readByte());
193
                                f.setDigital(i, base64InputStream.readByte());
194
                        for (int i=0; i<32; i++)
194
                        for (int i=0; i<32; i++)
195
                                f.setAnalog(i, base64InputStream.readSignedWord());
195
                                f.setAnalog(i, base64InputStream.readSignedWord());
196
                        result = f;
196
                        result = f;
197
                        break;
197
                        break;
198
                }
198
                }
199
                case 'F': {
199
                case 'F': {
200
                        ChangeParameterSetResponseFrame f = new ChangeParameterSetResponseFrame(address);
200
                        ChangeParameterSetResponseFrame f = new ChangeParameterSetResponseFrame(address);
201
                        f.setParameterSetNumber(base64InputStream.readByte());
201
                        f.setParameterSetNumber(base64InputStream.readByte());
202
                        result = f;
202
                        result = f;
203
                        break;
203
                        break;
204
                }
204
                }
205
                case 'G': {
205
                case 'G': {
206
                        ReadExternalControlResponseFrame f = new ReadExternalControlResponseFrame(address);
206
                        ReadExternalControlResponseFrame f = new ReadExternalControlResponseFrame(address);
207
                        f.setDigital(base64InputStream.readBytes(2));
207
                        f.setDigital(base64InputStream.readBytes(2));
208
                        f.setRemoteButtons(base64InputStream.readByte());
208
                        f.setRemoteButtons(base64InputStream.readByte());
209
                        f.setPitch(base64InputStream.readByte());
209
                        f.setPitch(base64InputStream.readByte());
210
                        f.setRoll(base64InputStream.readByte());
210
                        f.setRoll(base64InputStream.readByte());
211
                        f.setYaw(base64InputStream.readByte());
211
                        f.setYaw(base64InputStream.readByte());
212
                        f.setThrottle(base64InputStream.readByte());
212
                        f.setThrottle(base64InputStream.readByte());
213
                        f.setHeight(base64InputStream.readByte());
213
                        f.setHeight(base64InputStream.readByte());
214
                        f.setCommand(base64InputStream.readByte());
214
                        f.setCommand(base64InputStream.readByte());
215
                        f.setFrameNum(base64InputStream.readByte());
215
                        f.setFrameNum(base64InputStream.readByte());
216
                        f.setArgument(base64InputStream.readByte());
216
                        f.setArgument(base64InputStream.readByte());
217
                        result = f;
217
                        result = f;
218
                        break;
218
                        break;
219
                }
219
                }
220
                case 'H': {
220
                case 'H': {
221
                        AllDisplaysResponseFrame f = new AllDisplaysResponseFrame(address);
221
                        AllDisplaysResponseFrame f = new AllDisplaysResponseFrame(address);
222
                        f.setLine(base64InputStream.readByte());
222
                        f.setLine(base64InputStream.readByte());
223
                        //f.setMaxItem(getDataInputStream().readByte());
223
                        //f.setMaxItem(getDataInputStream().readByte());
224
                        f.setText(base64InputStream.readChars(20));
224
                        f.setText(base64InputStream.readChars(20));
225
                        result = f;
225
                        result = f;
226
                        break;
226
                        break;
227
                }
227
                }
228
                case 'k' : {
228
                case 'k' : {
229
                        CompassHeadingResponseFrame f = new CompassHeadingResponseFrame(address);
229
                        CompassHeadingResponseFrame f = new CompassHeadingResponseFrame(address);
230
                        base64InputStream.readSignedWords(2);
230
                        base64InputStream.readSignedWords(2);
231
                        base64InputStream.readBytes(2);
231
                        base64InputStream.readBytes(2);
232
                        base64InputStream.readByte();
232
                        base64InputStream.readByte();
233
                        base64InputStream.readByte();
233
                        base64InputStream.readByte();
234
                        result = f;
234
                        result = f;
235
                        break;
235
                        break;
236
                }
236
                }
237
                case 'L': {
237
                case 'L': {
238
                        AllDisplaysResponseFrame f = new AllDisplaysResponseFrame(address);
238
                        AllDisplaysResponseFrame f = new AllDisplaysResponseFrame(address);
239
                        f.setItem(base64InputStream.readByte());
239
                        f.setItem(base64InputStream.readByte());
240
                        // f.setMaxItem(getDataInputStream().readByte());
240
                        // f.setMaxItem(getDataInputStream().readByte());
241
                        f.setText(base64InputStream.readChars(80));
241
                        f.setText(base64InputStream.readChars(80));
242
                        result = f;
242
                        result = f;
243
                        break;
243
                        break;
244
                }
244
                }
245
                case 'O': {
245
                case 'O': {
246
                        OSDDataResponseFrame f = new OSDDataResponseFrame(address);
246
                        OSDDataResponseFrame f = new OSDDataResponseFrame(address);
247
                        f.setVersion(base64InputStream.readByte());
247
                        f.setVersion(base64InputStream.readByte());
248
                       
248
                       
249
                        GPSPosition pos = new GPSPosition();
249
                        GPSPosition pos = new GPSPosition();
250
                        pos.setLongitude(((double)base64InputStream.readSignedDWord())/1E7);
250
                        pos.setLongitude(((double)base64InputStream.readSignedDWord())/1E7);
251
                        pos.setLatitude(((double)base64InputStream.readSignedDWord())/1E7);
251
                        pos.setLatitude(((double)base64InputStream.readSignedDWord())/1E7);
252
                        pos.setAltitude(((double)base64InputStream.readSignedDWord())/1E3);
252
                        pos.setAltitude(((double)base64InputStream.readSignedDWord())/1E3);
253
                        pos.setStatus(base64InputStream.readByte());
253
                        pos.setStatus(base64InputStream.readByte());
254
                        f.setCurrentPosition(pos);
254
                        f.setCurrentPosition(pos);
255
                       
255
                       
256
                        pos = new GPSPosition();
256
                        pos = new GPSPosition();
257
                        pos.setLongitude(((double)base64InputStream.readSignedDWord())/1E7);
257
                        pos.setLongitude(((double)base64InputStream.readSignedDWord())/1E7);
258
                        pos.setLatitude(((double)base64InputStream.readSignedDWord())/1E7);
258
                        pos.setLatitude(((double)base64InputStream.readSignedDWord())/1E7);
259
                        pos.setAltitude(((double)base64InputStream.readSignedDWord())/1E3);
259
                        pos.setAltitude(((double)base64InputStream.readSignedDWord())/1E3);
260
                        pos.setStatus(base64InputStream.readByte());
260
                        pos.setStatus(base64InputStream.readByte());
261
                        f.setTargetPosition(pos);
261
                        f.setTargetPosition(pos);
262
                       
262
                       
263
                        GPSBearingAndRange rnb = new GPSBearingAndRange();
263
                        GPSBearingAndRange rnb = new GPSBearingAndRange();
264
                        rnb.setDistance(((double)base64InputStream.readWord())/10.0);
264
                        rnb.setDistance(((double)base64InputStream.readWord())/10.0);
265
                        rnb.setBearing(base64InputStream.readSignedWord());
265
                        rnb.setBearing(base64InputStream.readSignedWord());
266
                        f.setCurrentToTarget(rnb);
266
                        f.setCurrentToTarget(rnb);
267
 
267
 
268
                        pos = new GPSPosition();
268
                        pos = new GPSPosition();
269
                        pos.setLongitude(((double)base64InputStream.readSignedDWord())/1E7);
269
                        pos.setLongitude(((double)base64InputStream.readSignedDWord())/1E7);
270
                        pos.setLatitude(((double)base64InputStream.readSignedDWord())/1E7);
270
                        pos.setLatitude(((double)base64InputStream.readSignedDWord())/1E7);
271
                        pos.setAltitude(((double)base64InputStream.readSignedDWord())/1E3);
271
                        pos.setAltitude(((double)base64InputStream.readSignedDWord())/1E3);
272
                        pos.setStatus(base64InputStream.readByte());
272
                        pos.setStatus(base64InputStream.readByte());
273
                        f.setHomePosition(pos);
273
                        f.setHomePosition(pos);
274
                       
274
                       
275
                        rnb = new GPSBearingAndRange();
275
                        rnb = new GPSBearingAndRange();
276
                        rnb.setDistance(((double)base64InputStream.readWord())/10.0);
276
                        rnb.setDistance(((double)base64InputStream.readWord())/10.0);
277
                        rnb.setBearing(base64InputStream.readSignedWord());
277
                        rnb.setBearing(base64InputStream.readSignedWord());
278
                        f.setCurrentToHome(rnb);
278
                        f.setCurrentToHome(rnb);
279
                       
279
                       
280
                        f.setWaypointIndex(base64InputStream.readByte());
280
                        f.setWaypointIndex(base64InputStream.readByte());
281
                        f.setWaypointCount(base64InputStream.readByte());
281
                        f.setWaypointCount(base64InputStream.readByte());
282
                        f.setNumberOfSatellites(base64InputStream.readByte());
282
                        f.setNumberOfSatellites(base64InputStream.readByte());
283
                       
283
                       
284
                        // This stunt is a metric unit conversion: The height was supposed (H&I) to be in integral 5cm steps.
284
                        // This stunt is a metric unit conversion: The height was supposed (H&I) to be in integral 5cm steps.
285
                        // However there is error factor in the measurement of 24% too much.
285
                        // However there is error factor in the measurement of 24% too much.
286
                        // h[m] = h[int] * 0.05 / 1.24 = h[int]
286
                        // h[m] = h[int] * 0.05 / 1.24 = h[int]
287
                        f._setHeightByPressure(((double)base64InputStream.readSignedWord()) * 0.05 / 1.24);
287
                        f._setHeightByPressure(((double)base64InputStream.readSignedWord()) * 0.05 / 1.24);
288
                       
288
                       
289
                        f.setVerticalVelocityByPressure(((double)base64InputStream.readSignedWord()) * 0.05 / 1.24); // clueless!
289
                        f.setVerticalVelocityByPressure(((double)base64InputStream.readSignedWord()) * 0.05 / 1.24); // clueless!
290
                        f.setFlightTime(base64InputStream.readWord());
290
                        f.setFlightTime(base64InputStream.readWord());
291
                        f.setBatteryVoltage(base64InputStream.readByte());
291
                        f.setBatteryVoltage(base64InputStream.readByte());
292
                        f.setGroundSpeed(((double)base64InputStream.readWord()) / 1E2);
292
                        f.setGroundSpeed(((double)base64InputStream.readWord()) / 1E2);
293
                       
293
                       
294
                        f.setDirectionOfFlight(base64InputStream.readSignedWord());
294
                        f.setDirectionOfFlight(base64InputStream.readSignedWord());
295
                        f.setCompassHeading(base64InputStream.readSignedWord());
295
                        f.setCompassHeading(base64InputStream.readSignedWord());
296
                       
296
                       
297
                        f.setPitchAngle(base64InputStream.readSignedByte());
297
                        f.setPitchAngle(base64InputStream.readSignedByte());
298
                        f.setRollAngle(base64InputStream.readSignedByte());
298
                        f.setRollAngle(base64InputStream.readSignedByte());
299
                       
299
                       
300
                        f.setRcQuality(base64InputStream.readByte());
300
                        f.setRcQuality(base64InputStream.readByte());
301
                        f.setFcFlags(base64InputStream.readByte());
301
                        f.setFcFlags(base64InputStream.readByte());
302
                        f.setNcFlags(base64InputStream.readByte());
302
                        f.setNcFlags(base64InputStream.readByte());
303
                        f.setErrorCode(base64InputStream.readByte());
303
                        f.setErrorCode(base64InputStream.readByte());
304
                        f.setOperatingRadius(base64InputStream.readByte());
304
                        f.setOperatingRadius(base64InputStream.readByte());
305
                       
305
                       
306
                        f.setVerticalVelocityByGPS(((double)base64InputStream.readSignedWord()) / 1E2);
306
                        f.setVerticalVelocityByGPS(((double)base64InputStream.readSignedWord()) / 1E2);
307
                        f.setTargetLoiterTime(base64InputStream.readByte());
307
                        f.setTargetLoiterTime(base64InputStream.readByte());
308
                        f.setFcFlags2(base64InputStream.readByte());
308
                        f.setFcFlags2(base64InputStream.readByte());
309
                        f.setSetpointForAltitude(((double)base64InputStream.readSignedWord()) * 0.05 / 1.24);
309
                        f.setSetpointForAltitude(((double)base64InputStream.readSignedWord()) * 0.05 / 1.24);
310
                        f.setThrottle(base64InputStream.readByte());
310
                        f.setThrottle(base64InputStream.readByte());
311
                        f.setCurrent(base64InputStream.readWord());
311
                        f.setCurrent(base64InputStream.readWord());
312
                        f.setCapacityUsed(base64InputStream.readWord());
312
                        f.setCapacityUsed(base64InputStream.readWord());
313
                        result = f;
313
                        result = f;
314
                        break;
314
                        break;
315
}
315
}
316
                case 'S': {
316
                case 'S': {
317
                        UniversalWriteParamSetResponseFrame f = new UniversalWriteParamSetResponseFrame(address);
317
                        UniversalWriteParamSetResponseFrame f = new UniversalWriteParamSetResponseFrame(address);
318
                        f.setParameterSetNumber(base64InputStream.readByte());
318
                        f.setParameterSetNumber(base64InputStream.readByte());
319
                        result = f;
319
                        result = f;
320
                        break;
320
                        break;
321
                }
321
                }
322
                case 'T': {
322
                case 'T': {
323
                        MotorTestResponseFrame f = new MotorTestResponseFrame(address);
323
                        MotorTestResponseFrame f = new MotorTestResponseFrame(address);
324
                        result = f;
324
                        result = f;
325
                        break;
325
                        break;
326
                }
326
                }
327
                /*
327
                /*
328
                 * We have a collision with the 'x' token: Also used for VariablesRequest.
328
                 * We have a collision with the 'x' token: Also used for VariablesRequest.
329
                case 'x': {
329
                case 'x': {
330
                        LoopbackTestResponseFrame f = new LoopbackTestResponseFrame(address);
330
                        LoopbackTestResponseFrame f = new LoopbackTestResponseFrame(address);
331
                        f.setByte(getDataInputStream().readByte());
331
                        f.setByte(getDataInputStream().readByte());
332
                        f.setWord(getDataInputStream().readWord());
332
                        f.setWord(getDataInputStream().readWord());
333
                        f.setChararray(getDataInputStream().readChars(8));
333
                        f.setChararray(getDataInputStream().readChars(8));
334
                        result = f;
334
                        result = f;
335
                        break;
335
                        break;
336
                }
336
                }
337
            */
337
            */
338
                case 'V': {
338
                case 'V': {
339
                        VersionResponseFrame f = new VersionResponseFrame(address);
339
                        VersionResponseFrame f = new VersionResponseFrame(address);
340
                        f.setSWMajor(base64InputStream.readByte());
340
                        f.setSWMajor(base64InputStream.readByte());
341
                        f.setSWMinor(base64InputStream.readByte());
341
                        f.setSWMinor(base64InputStream.readByte());
342
                        f.setProtoMajor(base64InputStream.readByte());
342
                        f.setProtoMajor(base64InputStream.readByte());
343
                        f.setProtoMinor(base64InputStream.readByte());
343
                        f.setProtoMinor(base64InputStream.readByte());
344
                        f.setSWPatch(base64InputStream.readByte());
344
                        f.setSWPatch(base64InputStream.readByte());
345
                        f.setHardwareErrors(base64InputStream.readBytes(5));
345
                        f.setHardwareErrors(base64InputStream.readBytes(5));
346
                        result = f;
346
                        result = f;
347
                        break;
347
                        break;
348
                }
348
                }
349
               
349
               
350
                // This is my own creation. The ID collides with the waypoint one of FC.
350
                // This is my own creation. The ID collides with the waypoint one of FC.
351
                case 'X': {
351
                case 'X': {
352
                        VariablesResponseFrame f = new VariablesResponseFrame(address);
352
                        VariablesResponseFrame f = new VariablesResponseFrame(address);
353
                        f.setVariables(base64InputStream.readWords(8));
353
                        f.setVariables(base64InputStream.readWords(8));
354
                        result = f;
354
                        result = f;
355
                        break;
355
                        break;
356
                }
356
                }
357
                case 'w': {
357
                case 'w': {
358
                        SetCompassHeadingResponseFrame f = new SetCompassHeadingResponseFrame(address);
358
                        SetCompassHeadingResponseFrame f = new SetCompassHeadingResponseFrame(address);
359
                        // do stuff.
359
                        // do stuff.
360
                        /*
360
                        /*
361
                        ToMk3Mag.Attitude[0] = (int16_t)((10 * angle[PITCH]) / GYRO_DEG_FACTOR_PITCHROLL); // approx. 0.1 deg
361
                        ToMk3Mag.Attitude[0] = (int16_t)((10 * angle[PITCH]) / GYRO_DEG_FACTOR_PITCHROLL); // approx. 0.1 deg
362
                        ToMk3Mag.Attitude[1] = (int16_t)((10 * angle[ROLL]) / GYRO_DEG_FACTOR_PITCHROLL); // approx. 0.1 deg
362
                        ToMk3Mag.Attitude[1] = (int16_t)((10 * angle[ROLL]) / GYRO_DEG_FACTOR_PITCHROLL); // approx. 0.1 deg
363
                        ToMk3Mag.UserParam[0] = dynamicParams.UserParams[0];
363
                        ToMk3Mag.UserParam[0] = dynamicParams.UserParams[0];
364
                        ToMk3Mag.UserParam[1] = dynamicParams.UserParams[1];
364
                        ToMk3Mag.UserParam[1] = dynamicParams.UserParams[1];
365
                        ToMk3Mag.CalState = compassCalState;
365
                        ToMk3Mag.CalState = compassCalState;
366
                        */
366
                        */
367
                        // Waste 8 bytes to make CRC match.
367
                        // Waste 8 bytes to make CRC match.
368
                        base64InputStream.readBytes(8);
368
                        base64InputStream.readBytes(8);
369
                        result = f;
369
                        result = f;
370
                        break;
370
                        break;
371
                }
371
                }
372
                case 'Q':
372
                case 'Q':
373
                        UniversalReadParamSetResponseFrame f = new UniversalReadParamSetResponseFrame(address);
373
                        UniversalReadParamSetResponseFrame f = new UniversalReadParamSetResponseFrame(address);
374
                        f.setConfigurationSetNumber(base64InputStream.readByte());
374
                        f.setConfigurationSetNumber(base64InputStream.readByte());
375
                        f.setConfigurationVersion(base64InputStream.readByte());
375
                        f.setConfigurationVersion(base64InputStream.readByte());
376
                        int length = base64InputStream.readByte();
376
                        int length = base64InputStream.readByte();
377
                        f.setData(base64InputStream.readBytes(length));
377
                        f.setData(base64InputStream.readBytes(length));
378
                        result = f;
378
                        result = f;
379
                        break;
379
                        break;
380
                default:
380
                default:
381
                        int b;
-
 
382
                        int count = 0;
381
                        int count = 0;
383
                        while((b=read()) != '\r') {
382
                        while(read() != '\r') {
384
                                count++;
383
                                count++;
385
                        }
384
                        }
386
                        System.err.println("Unknown frame " + (char)iid + " received from " + address);
385
                        System.err.println("Unknown frame " + (char)iid + " received from " + address);
387
                        System.err.println("It appears to have " + (count-2) + " data bytes (encoded)");
386
                        System.err.println("It appears to have " + (count-2) + " data bytes (encoded)");
388
                        System.err.println("(" + (count-2) * 6/8 + " data bytes decoded)");
387
                        System.err.println("(" + (count-2) * 6/8 + " data bytes decoded)");
389
                        result = null;
388
                        result = null;
390
                }
389
                }
391
               
390
               
392
                int receivedCRC = (read() - '=') << 6;
391
                int receivedCRC = (read() - '=') << 6;
393
                receivedCRC += (read() - '=');
392
                receivedCRC += (read() - '=');
394
                crc %= 4096;
393
                crc %= 4096;
395
                if (receivedCRC != crc) {
394
                if (receivedCRC != crc) {
396
                        /// System.err.println("Expected CRC: " + crc + ", got CRC: " + receivedCRC);
395
                        /// System.err.println("Expected CRC: " + crc + ", got CRC: " + receivedCRC);
397
                        throw new IOException("CRC mismatch! Calculated crc: " + (int)crc + "; received check crc: " + receivedCRC + ", difference: " + Math.abs(crc - receivedCRC));
396
                        throw new IOException("CRC mismatch! Calculated crc: " + (int)crc + "; received check crc: " + receivedCRC + ", difference: " + Math.abs(crc - receivedCRC));
398
                }
397
                }
399
                if (read() != '\r') {
398
                if (read() != '\r') {
400
                        throw new IOException("CR at end of frame missing");
399
                        throw new IOException("CR at end of frame missing");
401
                }
400
                }
402
 
401
 
403
                return result;
402
                return result;
404
        }
403
        }
405
}
404
}
406
 
405