nrfcxx  0.1.0
C++-17 Framework for Nordic nRF5 Devices
contact.hpp
Go to the documentation of this file.
1 /* SPDX-License-Identifier: Apache-2.0 */
2 /* Copyright 2017-2019 Peter A. Bigot */
3 
7 #ifndef NRFCXX_SENSOR_CONTACT_HPP
8 #define NRFCXX_SENSOR_CONTACT_HPP
9 #pragma once
10 
11 #include <type_traits>
12 
13 #include <nrfcxx/clock.hpp>
14 #include <nrfcxx/gpio.hpp>
15 #include <nrfcxx/periph.hpp>
16 
17 namespace nrfcxx {
18 namespace sensor {
19 
20 namespace contact_internal {
21 
28 static constexpr auto utt_per_ts = 256U;
29 
30 template <typename INTEGRAL>
31 constexpr inline
32 INTEGRAL
33 ts_from_utt (INTEGRAL dur_utt)
34 {
35  return dur_utt / utt_per_ts;
36 }
37 
38 template <typename INTEGRAL>
39 constexpr inline
40 INTEGRAL
41 utt_from_ts (INTEGRAL dur_ts)
42 {
43  return dur_ts * utt_per_ts;
44 }
45 
46 } // ns contact_internals
47 
81 class contact
82 {
83 public:
85  static constexpr unsigned int HISTORY_LENGTH = 8;
86 
89  static constexpr unsigned int TIMESTAMP_Hz = contact_internal::ts_from_utt(clock::uptime::Frequency_Hz);
90 
92  template <typename INTEGRAL>
93  static constexpr INTEGRAL ts_from_ms (INTEGRAL dur_ms)
94  {
95  return contact_internal::ts_from_utt(clock::uptime::from_ms(dur_ms));
96  }
97 
99  template <typename INTEGRAL>
100  static constexpr INTEGRAL utt_from_ts (INTEGRAL dur_ts)
101  {
102  return contact_internal::utt_from_ts(dur_ts);
103  }
104 
108  using timestamp_type = uint64_t;
109 
112  using timediff_type = std::make_signed<uint64_t>::type;
113 
119  using reduced_timestamp_type = uint16_t;
120 
128  using duration_type = std::chrono::duration<timediff_type, std::ratio<1, TIMESTAMP_Hz>>;
129 
136  template <typename DurT = duration_type>
137  constexpr static DurT to_duration (timediff_type dts)
138  {
139  return std::chrono::duration_cast<DurT>(duration_type{dts});
140  }
141 
145 
147  using ordinal_type = uint16_t;
148 
155  struct state_type
156  {
157  using notify_fn = std::function<void(ordinal_type eo,
158  timestamp_type ts)>;
159 
171 
182 
190 
201 
206 
211  {
212  return captured_ts_;
213  }
214 
220  timestamp_type ordinal_ts () const;
221 
224  bool state_from_ordinal () const
225  {
227  }
228 
255  notify_fn notify = nullptr,
256  bool collapse = true) const;
257 
258  private:
259  // contact sets captured_ts_
260  friend class contact;
261 
264  timestamp_type captured_ts_;
265  };
266 
268  uint8_t const psel;
269 
281  using change_callback_bi = std::function<void(ordinal_type ordinal)>;
282 
291  contact (uint8_t psel,
292  change_callback_bi callback,
293  uint32_t pin_cnf = gpio::PIN_CNF_RDONLY);
294 
306  void record_change_bi (bool double_tap = false);
307 
327  {
328  return {[this](auto sp)
329  {
330  gpiote_sense_bi_(sp);
331  }};
332  }
333 
349  {
350  return {[this](periph::GPIOTE& instance)
351  {
352  gpiote_event_bi_(instance);
353  }};
354  }
355 
358  static timestamp_type now ()
359  {
360  return clock::uptime::now() >> 8;
361  }
362 
369  {
370  return clock::uptime::now24() >> 8;
371  }
372 
380  bool live_state () const
381  {
382  return (1U << psel) & nrf5::GPIO->IN;
383  }
384 
387  {
388  return (1 & eo);
389  }
390 
395  state_type snapshot () const;
396 
401  timestamp_type epoch_ts () const;
402 
403 protected:
407  bool recorded_state_bi_ () const
408  {
409  return state_from_ordinal(state_bi_.ordinal);
410  }
411 
412  void gpiote_sense_bi_ (const periph::GPIOTE::sense_status_type* sp);
413 
414  void gpiote_event_bi_ (periph::GPIOTE& instance)
415  {
416  bool double_tap = (live_state() == recorded_state_bi_());
417  record_change_bi(double_tap);
418  }
419 
420  change_callback_bi callback_;
421 
422  state_type volatile state_bi_;
423 };
424 
425 } // ns sensor
426 } // ns nrfcxx
427 
428 #endif /* NRFCXX_SENSOR_CONTACT_HPP */
nrfcxx::periph::GPIOTE::mutex_type
mutex_irq< GPIOTE_IRQn > mutex_type
An RAII type for mutex access to state that must be protected from GPIOTE interrupts.
Definition: periph.hpp:741
nrfcxx::periph::GPIOTE::event_listener
Object used to manage event callbacks.
Definition: periph.hpp:766
nrfcxx::sensor::contact::change_callback_bi
std::function< void(ordinal_type ordinal)> change_callback_bi
Signature for a contact state change notification.
Definition: contact.hpp:281
nrfcxx::sensor::contact
State and functionality related to monitoring dry contacts.
Definition: contact.hpp:81
nrfcxx::sensor::contact::event_listener
periph::GPIOTE::event_listener event_listener()
Construct a GPIOTE event listener for contact state changes.
Definition: contact.hpp:348
nrfcxx::sensor::contact::timediff_type
std::make_signed< uint64_t >::type timediff_type
The type used for full-scale time differences between event times.
Definition: contact.hpp:112
nrfcxx::sensor::contact::ts_from_ms
static constexpr INTEGRAL ts_from_ms(INTEGRAL dur_ms)
Calculate a timestamp duration derived from milliseconds.
Definition: contact.hpp:93
nrfcxx::sensor::contact::ordinal_type
uint16_t ordinal_type
The type used to store state changes event ordinals.
Definition: contact.hpp:147
nrfcxx::sensor::contact::record_change_bi
void record_change_bi(bool double_tap=false)
Update the ordinal to reflect a state change.
nrfcxx::clock::uptime::Frequency_Hz
constexpr static unsigned int Frequency_Hz
Frequency of the uptime clock as a symbolic constant.
Definition: clock.hpp:247
nrfcxx::sensor::contact::utt_from_ts
static constexpr INTEGRAL utt_from_ts(INTEGRAL dur_ts)
Calculate an uptime duration derived from timestamp ticks.
Definition: contact.hpp:100
nrfcxx::sensor::contact::HISTORY_LENGTH
static constexpr unsigned int HISTORY_LENGTH
The number of timestamped state changes recorded.
Definition: contact.hpp:85
nrfcxx::sensor::contact::state_type
An aggregate capturing consistent contact state.
Definition: contact.hpp:155
nrfcxx::sensor::contact::reduced_timestamp_type
uint16_t reduced_timestamp_type
The type used for stored contact state changes.
Definition: contact.hpp:119
nrfcxx::sensor::contact::live_state
bool live_state() const
Read the contact state.
Definition: contact.hpp:380
clock.hpp
Core clock-related functionality.
nrfcxx::sensor::contact::state_type::live_state
bool live_state
A record of the actual GPIO state at the time a contact snapshot is captured.
Definition: contact.hpp:189
nrfcxx::periph::GPIOTE::sense_listener
Object used to manage sense callbacks.
Definition: periph.hpp:854
nrfcxx::periph::GPIOTE
Class supporting GPIO task and event operations.
Definition: periph.hpp:639
nrfcxx::mutex_irq
nvic_BlockIRQ as a template type.
Definition: core.hpp:497
nrfcxx::sensor::contact::now
static timestamp_type now()
Get the full-scale current time in the representation of recorded contact events.
Definition: contact.hpp:358
nrfcxx::sensor::contact::timestamp_type
uint64_t timestamp_type
The type used for full-scale contact state change event times.
Definition: contact.hpp:108
nrfcxx::sensor::contact::timestamp
static reduced_timestamp_type timestamp()
Get the reduced-range current time in the representation of recorded contact events.
Definition: contact.hpp:368
gpio.hpp
Core GPIO functionality.
nrfcxx::sensor::contact::state_type::time_of_change
reduced_timestamp_type time_of_change() const
As above but returns the time of the most recent change.
nrfcxx::gpio::PIN_CNF_RDONLY
constexpr uint32_t PIN_CNF_RDONLY
GPIO pin configuration for input only.
Definition: gpio.hpp:22
nrfcxx::sensor::contact::psel
uint8_t const psel
The GPIO pin on which the contact is monitored.
Definition: contact.hpp:268
nrfcxx::sensor::contact::contact
contact(uint8_t psel, change_callback_bi callback, uint32_t pin_cnf=gpio::PIN_CNF_RDONLY)
Construct and configure a contact with callback on change.
nrfcxx::periph::GPIOTE::sense_status_type
Structure used to convey information about pin levels to sense_listener callbacks.
Definition: periph.hpp:672
nrfcxx::clock::uptime::now24
static unsigned int now24()
Low 24 bits of the uptime counter.
Definition: clock.hpp:300
nrfcxx::sensor::contact::state_type::state_from_ordinal
bool state_from_ordinal() const
Get the contact state corresponding to the last recorded event.
Definition: contact.hpp:224
nrfcxx::sensor::contact::snapshot
state_type snapshot() const
Return a consistent snapshot of the contact state.
nrfcxx::sensor::contact::state_from_ordinal
static bool state_from_ordinal(ordinal_type eo)
Synthesize pin state from an event ordinal.
Definition: contact.hpp:386
nrfcxx::sensor::contact::state_type::event_ts
reduced_timestamp_type event_ts[HISTORY_LENGTH]
Timestamps of recent contact state change events.
Definition: contact.hpp:170
nrfcxx::clock::uptime::now
static uint64_t now()
Full-range uptime counter.
nrfcxx::sensor::contact::TIMESTAMP_Hz
static constexpr unsigned int TIMESTAMP_Hz
The clock rate used to record state transition timestamps.
Definition: contact.hpp:89
nrfcxx::sensor::contact::state_type::captured_ts
timestamp_type captured_ts() const
The absolute time at which the snapshot was taken.
Definition: contact.hpp:210
nrfcxx::sensor::contact::state_type::ordinal_ts
timestamp_type ordinal_ts() const
Calculate the absolute time of the ordinal event.
nrfcxx::clock::uptime::from_ms
constexpr static int64_t from_ms(int64_t ms)
Convert integral milliseconds to uptime ticks (rounding down).
Definition: clock.hpp:422
nrfcxx::sensor::contact::duration_type
std::chrono::duration< timediff_type, std::ratio< 1, TIMESTAMP_Hz > > duration_type
Full precision duration type for timestamp clock.
Definition: contact.hpp:128
nrfcxx::sensor::contact::epoch_ts
timestamp_type epoch_ts() const
The absolute time at which the contact initial state was captured.
nrfcxx::sensor::contact::state_type::process_changes
timestamp_type process_changes(const state_type &prev, notify_fn notify=nullptr, bool collapse=true) const
Assess the changes between a previous snapshot and this one.
nrfcxx::sensor::contact_internal::utt_per_ts
static constexpr auto utt_per_ts
Divisor to convert from uptime ticks to contact timestamp clock ticks.
Definition: contact.hpp:28
nrfcxx::sensor::contact::state_type::ordinal
ordinal_type ordinal
The lower bits of a ordinal of state change events.
Definition: contact.hpp:181
periph.hpp
Abstraction of Nordic device peripherals.
nrfcxx
Primary namespace for nrfcxx functionality.
Definition: clock.hpp:17
nrfcxx::sensor::contact::to_duration
constexpr static DurT to_duration(timediff_type dts)
Generic conversion from timestamp ticks to a std::chrono::duration type.
Definition: contact.hpp:137
nrfcxx::sensor::contact::sense_listener
periph::GPIOTE::sense_listener sense_listener()
Construct a GPIOTE sense listener for contact state changes.
Definition: contact.hpp:326
nrfcxx::sensor::contact::recorded_state_bi_
bool recorded_state_bi_() const
Return the last confirmed contact state.
Definition: contact.hpp:407