Statistics
| Branch: | Tag: | Revision:

amiro-lld / source / deca_instance_common.c @ 9e45662e

History | View | Annotate | Download (34.084 KB)

1
/*! ----------------------------------------------------------------------------
2
 *  @file    instance_common.c
3
 *  @brief   DecaWave application level common instance functions
4
 *
5
 * @attention
6
 *
7
 * Copyright 2015 (c) DecaWave Ltd, Dublin, Ireland.
8
 *
9
 * All rights reserved.
10
 *
11
 * @author DecaWave
12
 */
13

    
14

    
15

    
16
#include <deca_instance.h>
17
#if defined(AMIROLLD_CFG_USE_DW1000) || defined(__DOXYGEN__)
18

    
19

    
20
#include <alld_dw1000.h>
21
#include <string.h>
22
#include <math.h>
23

    
24

    
25

    
26
extern double dwt_getrangebias(uint8_t chan, float range, uint8_t prf);
27

    
28
extern const uint16_t rfDelays[2];
29
extern const uint16_t rfDelaysTREK[2];
30
extern const tx_struct txSpectrumConfig[8];
31

    
32

    
33

    
34
// -------------------------------------------------------------------------------------------------------------------
35
// Deca Calibration Values
36
// -------------------------------------------------------------------------------------------------------------------
37

    
38
#define DWT_PRF_64M_RFDLY   (514.462f)
39
#define DWT_PRF_16M_RFDLY   (513.9067f)
40

    
41
// -------------------------------------------------------------------------------------------------------------------
42

    
43
//The table below specifies the default TX spectrum configuration parameters... this has been tuned for DW EVK hardware units
44
//the table is set for smart power - see below in the instance_config function how this is used when not using smart power
45
const tx_struct txSpectrumConfig[8] =
46
{
47
    //Channel 0 ----- this is just a place holder so the next array element is channel 1
48
    {
49
            0x0,   //0
50
            {
51
                    0x0, //0
52
                    0x0 //0
53
            }
54
    },
55
    //Channel 1
56
    {
57
            0xc9,   //PG_DELAY
58
            {
59
                    0x15355575, //16M prf power
60
                    0x07274767 //64M prf power
61
            }
62

    
63
    },
64
    //Channel 2
65
    {
66
            0xc2,   //PG_DELAY
67
            {
68
                    0x15355575, //16M prf power
69
                    0x07274767 //64M prf power
70
            }
71
    },
72
    //Channel 3
73
    {
74
            0xc5,   //PG_DELAY
75
            {
76
                    0x0f2f4f6f, //16M prf power
77
                    0x2b4b6b8b //64M prf power
78
            }
79
    },
80
    //Channel 4
81
    {
82
            0x95,   //PG_DELAY
83
            {
84
                    0x1f1f3f5f, //16M prf power
85
                    0x3a5a7a9a //64M prf power
86
            }
87
    },
88
    //Channel 5
89
    {
90
            0xc0,   //PG_DELAY
91
            {
92
                    0x0E082848, //16M prf power
93
                    0x25456585 //64M prf power
94
            }
95
    },
96
    //Channel 6 ----- this is just a place holder so the next array element is channel 7
97
    {
98
            0x0,   //0
99
            {
100
                    0x0, //0
101
                    0x0 //0
102
            }
103
    },
104
    //Channel 7
105
    {
106
            0x93,   //PG_DELAY
107
            {
108
                    0x32527292, //16M prf power
109
                    0x5171B1d1 //64M prf power
110
            }
111
    }
112
};
113

    
114
//these are default antenna delays for EVB1000, these can be used if there is no calibration data in the DW1000,
115
//or instead of the calibration data
116
const uint16_t rfDelays[2] = {
117
        (uint16_t) ((DWT_PRF_16M_RFDLY/ 2.0) * 1e-9 / DWT_TIME_UNITS),//PRF 16
118
        (uint16_t) ((DWT_PRF_64M_RFDLY/ 2.0) * 1e-9 / DWT_TIME_UNITS)
119
};
120

    
121
//these are default TREK Tag/Anchor antenna delays
122
const uint16_t rfDelaysTREK[2] = {
123
        (uint16_t) ((514.83f/ 2.0) * 1e-9 / DWT_TIME_UNITS),//channel 2
124
        (uint16_t) ((514.65f/ 2.0) * 1e-9 / DWT_TIME_UNITS) //channel 5
125
};
126

    
127
//int instance_starttxtest(int framePeriod)
128
//{
129
//    //define some test data for the tx buffer
130
//    uint8 msg[127] = "The quick brown fox jumps over the lazy dog. The quick brown fox jumps over the lazy dog. The quick brown fox jumps over the l";
131

    
132
//    //NOTE: SPI frequency must be < 3MHz
133
//    port_set_dw1000_slowrate();  //max SPI before PLLs configured is ~4M
134

    
135
//    // the value here 0x1000 gives a period of 32.82 µs
136
//    //this is setting 0x1000 as frame period (125MHz clock cycles) (time from Tx en - to next - Tx en)
137
//    dwt_configcontinuousframemode(framePeriod);
138

    
139
//    dwt_writetxdata(127, (uint8 *)  msg, 0) ;
140
//    dwt_writetxfctrl(127, 0, 0);
141

    
142
//    //to start the first frame - set TXSTRT
143
//    dwt_starttx(DWT_START_TX_IMMEDIATE);
144

    
145
//    //measure the power
146
//    //Spectrum Analyser set:
147
//    //FREQ to be channel default e.g. 3.9936 GHz for channel 2
148
//    //SPAN to 1GHz
149
//    //SWEEP TIME 1s
150
//    //RBW and VBW 1MHz
151
//    //measure channel power
152

    
153
//    return DWT_SUCCESS ;
154
//}
155

    
156
// -------------------------------------------------------------------------------------------------------------------
157
//      Data Definitions
158
// -------------------------------------------------------------------------------------------------------------------
159

    
160
static instance_data_t instance_data[NUM_INST] ;
161

    
162
static double inst_tdist[MAX_TAG_LIST_SIZE] ;
163
static double inst_idist[MAX_ANCHOR_LIST_SIZE] ;
164
static double inst_idistraw[MAX_ANCHOR_LIST_SIZE] ;
165

    
166
// -------------------------------------------------------------------------------------------------------------------
167
// Functions
168
// -------------------------------------------------------------------------------------------------------------------
169

    
170

    
171
/* @fn           instance_get_local_structure_ptr
172
 * @brief function to return the pointer to local instance data structure
173
 * */
174
instance_data_t* instance_get_local_structure_ptr(unsigned int x)
175
{
176
        if (x >= NUM_INST)
177
        {
178
                return NULL;
179
        }
180

    
181
        return &instance_data[x];
182
}
183

    
184

    
185
// -------------------------------------------------------------------------------------------------------------------
186
/* @fn           instance_convert_usec_to_devtimeu
187
 * @brief function to convert microseconds to device time
188
 * */
189
uint64_t instance_convert_usec_to_devtimeu (double microsecu)
190
{
191
    uint64_t dt;
192
    long double dtime;
193

    
194
    dtime = (microsecu / (double) DWT_TIME_UNITS) / 1e6 ;
195

    
196
    dt =  (uint64_t) (dtime) ;
197

    
198
    return dt;
199
}
200

    
201
/* @fn           instance_calculate_rangefromTOF
202
 * @brief function to calculate and the range from given Time of Flight
203
 * */
204
int instance_calculate_rangefromTOF(int idx, uint32_t tofx)
205
{
206
                instance_data_t* inst = instance_get_local_structure_ptr(0);
207
        double distance ;
208
        double distance_to_correct;
209
        double tof ;
210
        int32_t tofi ;
211

    
212
        // check for negative results and accept them making them proper negative integers
213
        tofi = (int32_t) tofx ; // make it signed
214
        if (tofi > 0x7FFFFFFF)  // close up TOF may be negative
215
        {
216
            tofi -= 0x80000000 ;  //
217
        }
218

    
219
        // convert device time units to seconds (as floating point)
220
        tof = tofi * DWT_TIME_UNITS ;
221
        inst_idistraw[idx] = distance = tof * SPEED_OF_LIGHT;
222

    
223
#if (CORRECT_RANGE_BIAS == 1)
224
        //for the 6.81Mb data rate we assume gating gain of 6dB is used,
225
        //thus a different range bias needs to be applied
226
        //if(inst->configData.dataRate == DWT_BR_6M8)
227
        if(inst->smartPowerEn)
228
        {
229
                //1.31 for channel 2 and 1.51 for channel 5
230
                if(inst->configData.chan == 5)
231
                {
232
                        distance_to_correct = distance/1.51;
233
                }
234
                else //channel 2
235
                {
236
                        distance_to_correct = distance/1.31;
237
                        }
238
        }
239
        else
240
        {
241
                distance_to_correct = distance;
242
        }
243

    
244
        distance = distance - dwt_getrangebias(inst->configData.chan, (float) distance_to_correct, inst->configData.prf);
245
#endif
246

    
247
        if ((distance < 0) || (distance > 20000.000))    // discard any results less than <0 cm or >20 km
248
            return 0;
249

    
250
        inst_idist[idx] = distance;
251

    
252
        inst->longTermRangeCount++ ;                          // for computing a long term average
253

    
254
    return 1;
255
}// end of calculateRangeFromTOF
256

    
257
void instance_set_tagdist(int tidx, int aidx)
258
{
259
        inst_tdist[tidx] = inst_idist[aidx];
260
}
261

    
262
double instance_get_tagdist(int idx)
263
{
264
        return inst_tdist[idx];
265
}
266

    
267
void instance_cleardisttable(int idx)
268
{
269
        inst_idistraw[idx] = 0;
270
        inst_idist[idx] = 0;
271
}
272

    
273
void instance_cleardisttableall(void)
274
{
275
        int i;
276

    
277
        for(i=0; i<MAX_ANCHOR_LIST_SIZE; i++)
278
        {
279
                inst_idistraw[i] = 0xffff;
280
                inst_idist[i] = 0xffff;
281
        }
282
}
283

    
284
// -------------------------------------------------------------------------------------------------------------------
285
// Set this instance role as the Tag, Anchor
286
/*void instance_set_role(int inst_mode)
287
{
288
    // assume instance 0, for this
289
    inst->mode =  inst_mode;                   // set the role
290
}
291
*/
292
int instance_get_role(void)
293
{
294
        instance_data_t* inst = instance_get_local_structure_ptr(0);
295

    
296
    return inst->mode;
297
}
298

    
299
int instance_newrange(void)
300
{
301
        instance_data_t* inst = instance_get_local_structure_ptr(0);
302
        int x = inst->newRange;
303
    inst->newRange = TOF_REPORT_NUL;
304
    return x;
305
}
306

    
307
int instance_newrangeancadd(void)
308
{
309
        instance_data_t* inst = instance_get_local_structure_ptr(0);
310
    return inst->newRangeAncAddress;
311
}
312

    
313
int instance_newrangetagadd(void)
314
{
315
        instance_data_t* inst = instance_get_local_structure_ptr(0);
316
    return inst->newRangeTagAddress;
317
}
318

    
319
int instance_newrangetim(void)
320
{
321
        instance_data_t* inst = instance_get_local_structure_ptr(0);
322
    return inst->newRangeTime;
323
}
324

    
325
// -------------------------------------------------------------------------------------------------------------------
326
// function to clear counts/averages/range values
327
//
328
void instance_clearcounts(void)
329
{
330
        instance_data_t* inst = instance_get_local_structure_ptr(0);
331
    int i= 0 ;
332

    
333
    //inst->rxTimeouts = 0 ;
334
    //inst->txMsgCount = 0 ;
335
    //inst->rxMsgCount = 0 ;
336

    
337
    dwt_configeventcounters(1); //enable and clear - NOTE: the counters are not preserved when in DEEP SLEEP
338

    
339
    inst->frameSN = 0;
340

    
341
    inst->longTermRangeCount  = 0;
342

    
343

    
344
    for(i=0; i<MAX_ANCHOR_LIST_SIZE; i++)
345
        {
346
            inst->tofArray[i] = INVALID_TOF;
347
        }
348

    
349
    for(i=0; i<MAX_TAG_LIST_SIZE; i++)
350
        {
351
                inst->tof[i] = INVALID_TOF;
352
        }
353

    
354
} // end instanceclearcounts()
355

    
356

    
357
// -------------------------------------------------------------------------------------------------------------------
358
// function to initialise instance structures
359
//
360
// Returns 0 on success and -1 on error
361
int instance_init(int inst_mode, DW1000Driver* drv)
362
{
363
        instance_data_t* inst = instance_get_local_structure_ptr(0);
364
    int result;
365

    
366
    inst->mode =  inst_mode;                                // assume listener,
367
    inst->twrMode = LISTENER;
368
    inst->testAppState = TA_INIT ;
369
    inst->instToSleep = FALSE;
370

    
371

    
372
    // Reset the IC (might be needed if not getting here from POWER ON)
373
    // ARM code: Remove soft reset here as using hard reset in the inittestapplication() in the main.c file
374
    //dwt_softreset();
375

    
376
        //this initialises DW1000 and uses specified configurations from OTP/ROM
377