-
Notifications
You must be signed in to change notification settings - Fork 13
/
Copy pathBTLEDecoder.cpp
94 lines (85 loc) · 2.92 KB
/
BTLEDecoder.cpp
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
// Copyright (c) 2016-2016 Josh Blum
// SPDX-License-Identifier: BSL-1.0
#include <Pothos/Framework.hpp>
#include "BTLEUtils.hpp"
#include <iostream>
#include <cmath>
/***********************************************************************
* |PothosDoc BTLE Decoder
*
* Decode bluetooth low energy packets.
* The decoder block accepts a stream of real-valued samples on input port 0,
* and produces a message containing keyword value pairs on output port 0.
*
* <h2>Input format</h2>
*
* The input port expects either signed integers that have been frequency demodulated
* or alternatively, frequency demodulated floating point samples between -pi and +pi.
* The scaling of the input samples does not matter, and the input sample rate should be 2 Msps.
* A typical upstream flow involves raw complex baseband samples and the "Freq Demod" block.
*
* <h2>Output format</h2>
*
* Each decoded BTLE packet results in a dictionary message of type Pothos::ObjectKwargs.
* The keyword and value pairs correspond with the fields in the BTLE packet.
*
* |category /Decode
* |keywords bluetooth low energy
*
* |factory /btle/btle_decoder()
**********************************************************************/
class BTLEDecoder : public Pothos::Block
{
public:
BTLEDecoder(void)
{
this->setupInput(0); //unspecified type, handles conversion
this->setupOutput(0);
}
static Block *make(void)
{
return new BTLEDecoder();
}
void work(void)
{
auto inPort = this->input(0);
auto inBuff = inPort->buffer();
auto N = inBuff.elements();
if (N == 0) return; //nothing available
//floating point support
if (inBuff.dtype.isFloat())
{
auto float32Buff = inBuff.convert(typeid(float));
auto in = float32Buff.as<const float *>();
const float gain = (1 << 15)/M_PI;
for (size_t i = 0; i < N; i++)
{
if (_decoder.feedOne(uint16_t(in[i]*gain)))
{
this->output(0)->postMessage(_decoder.packetData);
//std::cout << Pothos::Object(_decoder.packetData).toString() << std::endl;
}
}
}
//fixed point support
else
{
auto int16Buff = inBuff.convert(typeid(int16_t));
auto in = int16Buff.as<const uint16_t *>();
for (size_t i = 0; i < N; i++)
{
if (_decoder.feedOne(in[i]))
{
this->output(0)->postMessage(_decoder.packetData);
//std::cout << Pothos::Object(_decoder.packetData).toString() << std::endl;
}
}
}
//consume all input elements
inPort->consume(inPort->elements());
}
private:
BTLEUtilsDecoder _decoder;
};
static Pothos::BlockRegistry registerBTLEDecoder(
"/btle/btle_decoder", &BTLEDecoder::make);