Ersa Wearable Platform
Embedded smartwatch firmware and application framework
Loading...
Searching...
No Matches
apple_notifications.h
Go to the documentation of this file.
1#pragma once
2#include <stdint.h>
3#include <stddef.h>
4#include <string.h>
5
6namespace ersa { namespace protocols {
7
9inline uint32_t readLe32(const uint8_t* p) {
10 return uint32_t(p[0]) | (uint32_t(p[1]) << 8) |
11 (uint32_t(p[2]) << 16) | (uint32_t(p[3]) << 24);
12}
14inline void writeLe32(uint8_t* p, uint32_t value) {
15 for (unsigned i = 0; i < 4; ++i) p[i] = uint8_t(value >> (8 * i));
16}
17
27public:
29 enum class Result { More, Complete, Invalid };
35 void begin(uint32_t uid, bool includeNegativeAction = false) {
36 uid_ = uid; size_ = 0; includeNegativeAction_ = includeNegativeAction;
37 title[0] = message[0] = negativeActionLabel[0] = 0;
38 }
44 Result feed(const uint8_t* data, size_t length) {
45 if (length > sizeof(bytes_) - size_) return Result::Invalid;
46 memcpy(bytes_ + size_, data, length);
47 size_ += length;
48 if (size_ < 5) return Result::More;
49 if (bytes_[0] != 0 || readLe32(bytes_ + 1) != uid_) return Result::Invalid;
50 size_t pos = 5;
51 const unsigned count = includeNegativeAction_ ? 3 : 2;
52 for (unsigned i = 0; i < count; ++i) {
53 if (size_ - pos < 3) return Result::More;
54 const uint8_t id = bytes_[pos];
55 const size_t len = bytes_[pos + 1] | (size_t(bytes_[pos + 2]) << 8);
56 const uint8_t expectedId = i == 0 ? 1 : (i == 1 ? 3 : 7);
57 const size_t capacity = i == 0 ? sizeof(title) : (i == 1 ? sizeof(message) : sizeof(negativeActionLabel));
58 if (id != expectedId || len >= capacity) return Result::Invalid;
59 pos += 3;
60 if (size_ - pos < len) return Result::More;
61 char* out = i == 0 ? title : (i == 1 ? message : negativeActionLabel);
62 memcpy(out, bytes_ + pos, len);
63 out[len] = 0;
64 pos += len;
65 }
66 return pos == size_ ? Result::Complete : Result::Invalid;
67 }
73 static void request(uint32_t uid, bool includeNegativeAction, uint8_t* out) {
74 out[0] = 0;
75 writeLe32(out + 1, uid);
76 out[5] = 1; out[6] = 31; out[7] = 0;
77 out[8] = 3; out[9] = 63; out[10] = 0;
78 if (includeNegativeAction) {
79 // Action labels are variable-length attributes without a
80 // requested-length parameter in the ANCS command format.
81 out[11] = 7;
82 }
83 }
85 static void request(uint32_t uid, uint8_t (&out)[11]) {
86 request(uid, false, out);
87 }
93 char normalized[sizeof(negativeActionLabel)]{};
94 size_t n = 0;
95 for (const char* p = negativeActionLabel; *p && n + 1 < sizeof(normalized); ++p) {
96 const char c = *p;
97 if (c == ' ' || c == '\t' || c == '\r' || c == '\n') continue;
98 normalized[n++] = (c >= 'A' && c <= 'Z') ? char(c - 'A' + 'a') : c;
99 }
100 return strcmp(normalized, "dismiss") == 0 || strcmp(normalized, "clear") == 0;
101 }
102 char title[32]{};
103 char message[64]{};
105private:
106 uint32_t uid_{0};
108 uint8_t bytes_[140]{};
109 size_t size_{0};
110};
111
118struct AncsCall {
120 uint32_t uid{0};
122 uint8_t flags{0};
124 bool ringing{false};
126 void update(uint32_t id, uint8_t eventFlags) { uid = id; flags = eventFlags; ringing = true; }
128 bool remove(uint32_t id) {
129 if (!ringing || id != uid) return false;
130 ringing = false;
131 return true;
132 }
137 bool action(uint32_t id, bool positive, uint8_t (&out)[6]) const {
138 if (!ringing || id != uid || !(flags & (positive ? 8 : 16))) return false;
139 out[0] = 2; writeLe32(out + 1, uid); out[5] = positive ? 0 : 1;
140 return true;
141 }
142};
143
144} } // namespace ersa::protocols
Definition apple_notifications.h:26
Result feed(const uint8_t *data, size_t length)
Definition apple_notifications.h:44
uint32_t uid_
Definition apple_notifications.h:106
static void request(uint32_t uid, bool includeNegativeAction, uint8_t *out)
Definition apple_notifications.h:73
size_t size_
Definition apple_notifications.h:109
bool includeNegativeAction_
Definition apple_notifications.h:107
Result
Definition apple_notifications.h:29
uint8_t bytes_[140]
Definition apple_notifications.h:108
char negativeActionLabel[32]
Definition apple_notifications.h:104
void begin(uint32_t uid, bool includeNegativeAction=false)
Definition apple_notifications.h:35
static void request(uint32_t uid, uint8_t(&out)[11])
Definition apple_notifications.h:85
bool negativeActionIsDismissal() const
Definition apple_notifications.h:92
char title[32]
Definition apple_notifications.h:102
char message[64]
Definition apple_notifications.h:103
void writeLe32(uint8_t *p, uint32_t value)
Definition apple_notifications.h:14
uint32_t readLe32(const uint8_t *p)
Definition apple_notifications.h:9
Definition application.h:10
char data[MANIFEST_LIMIT]
Definition ota_service.cpp:33
size_t length
Definition ota_service.cpp:34
Definition apple_notifications.h:118
bool remove(uint32_t id)
Definition apple_notifications.h:128
uint8_t flags
Definition apple_notifications.h:122
void update(uint32_t id, uint8_t eventFlags)
Definition apple_notifications.h:126
bool action(uint32_t id, bool positive, uint8_t(&out)[6]) const
Definition apple_notifications.h:137
uint32_t uid
Definition apple_notifications.h:120
bool ringing
Definition apple_notifications.h:124