summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNicholas Van Doorn <vandoorn.nick@gmail.com>2018-10-25 11:49:43 -0700
committerGitHub <noreply@github.com>2018-10-25 11:49:43 -0700
commit51157058bb955e173901e3436968254923b2a5be (patch)
treed68cb23e443c0e0c5a06b768f099cb18d5e29e10
parent8b0c2ec5fbca5c562a62eeed5583dff0bf0d1bc0 (diff)
parent86aae1611e3b75e41a2d1ff28eef08d8de038f72 (diff)
Merge pull request #6 from brnkl/has-changed-api
Implement "has changed" API
-rw-r--r--brnkl_motion.api3
-rw-r--r--motionMonitor/motionMonitor.c114
2 files changed, 62 insertions, 55 deletions
diff --git a/brnkl_motion.api b/brnkl_motion.api
index ad4262a..247329c 100644
--- a/brnkl_motion.api
+++ b/brnkl_motion.api
@@ -6,6 +6,9 @@ FUNCTION le_result_t getSuddenImpact(
double z [N_CHANGE_BLOCKS] OUT,
uint64 timestamps[N_CHANGE_BLOCKS] OUT
);
+
+FUNCTION int8 hasSuddenImpact();
+
FUNCTION le_result_t getCurrentAcceleration(
double x OUT,
double y OUT,
diff --git a/motionMonitor/motionMonitor.c b/motionMonitor/motionMonitor.c
index 2622ea6..c56a55c 100644
--- a/motionMonitor/motionMonitor.c
+++ b/motionMonitor/motionMonitor.c
@@ -5,20 +5,10 @@
#define N_CHANGE_BLOCKS 200
#define SAMPLE_PERIOD_MS 100
+#define DEFAULT_THRESHOLD_MS2 17
void* impactMonitor(void*);
-typedef struct {
- double x;
- double y;
- double z;
-} Acceleration;
-
-double xAccImpact[N_CHANGE_BLOCKS];
-double yAccImpact[N_CHANGE_BLOCKS];
-double zAccImpact[N_CHANGE_BLOCKS];
-uint64_t timestamps[N_CHANGE_BLOCKS];
-
static const char FormatStr[] = "/sys/bus/iio/devices/iio:device0/in_%s_%s";
static const char AccType[] = "accel";
static const char GyroType[] = "anglvel";
@@ -26,18 +16,20 @@ static const char CompX[] = "x_raw";
static const char CompY[] = "y_raw";
static const char CompZ[] = "z_raw";
static const char CompScale[] = "scale";
-int totalImpacts = 0;
-static const double impactThreshold = 20.0;
-
-Acceleration suddenImpact = {0, 0, 0};
-pthread_t impactThread;
-pthread_mutex_t impactMutex;
+struct suddenImpacts_t {
+ int nValues;
+ double threshold;
+ double x[N_CHANGE_BLOCKS];
+ double y[N_CHANGE_BLOCKS];
+ double z[N_CHANGE_BLOCKS];
+ uint64_t timestamps[N_CHANGE_BLOCKS];
+ pthread_mutex_t lock;
+} impacts = {0, DEFAULT_THRESHOLD_MS2};
/*
* Reports the x, y and z accelerometer readings in meters per second squared.
-*/
-
+ */
le_result_t brnkl_motion_getCurrentAcceleration(double* xAcc,
double* yAcc,
double* zAcc) {
@@ -73,21 +65,27 @@ done:
return r;
}
-le_result_t recordImpact(double* xAcc, double* yAcc, double* zAcc) {
- if (totalImpacts > N_CHANGE_BLOCKS || totalImpacts > N_CHANGE_BLOCKS ||
- totalImpacts > N_CHANGE_BLOCKS)
+le_result_t recordImpact(struct suddenImpacts_t* it,
+ double xAcc,
+ double yAcc,
+ double zAcc) {
+ if (it->nValues > N_CHANGE_BLOCKS || it->nValues > N_CHANGE_BLOCKS ||
+ it->nValues > N_CHANGE_BLOCKS)
return LE_OUT_OF_RANGE;
- timestamps[totalImpacts] = GetCurrentTimestamp();
- xAccImpact[totalImpacts] = *xAcc;
- yAccImpact[totalImpacts] = *yAcc;
- zAccImpact[totalImpacts] = *zAcc;
- totalImpacts++;
- LE_INFO("New Impact, totalImpacts: %d", totalImpacts);
+ it->timestamps[it->nValues] = GetCurrentTimestamp();
+ it->x[it->nValues] = xAcc;
+ it->y[it->nValues] = yAcc;
+ it->z[it->nValues] = zAcc;
+ it->nValues++;
return LE_OK;
}
+int8_t brnkl_motion_hasSuddenImpact() {
+ return impacts.nValues > 0;
+}
+
le_result_t brnkl_motion_getSuddenImpact(double* xAcc,
size_t* xSize,
double* yAcc,
@@ -96,67 +94,73 @@ le_result_t brnkl_motion_getSuddenImpact(double* xAcc,
size_t* zSize,
uint64_t* timestampssOut,
size_t* timeSize) {
- if (!totalImpacts)
+ if (!impacts.nValues)
LE_INFO("No Sudden Impacts to Report");
else {
- pthread_mutex_lock(&impactMutex);
- // check
+ pthread_mutex_lock(&impacts.lock);
- if (totalImpacts > *xSize || totalImpacts > *ySize || totalImpacts > *zSize)
+ if (impacts.nValues > *xSize || impacts.nValues > *ySize ||
+ impacts.nValues > *zSize)
return LE_OUT_OF_RANGE;
- for (int i = 0; i < totalImpacts; i++) {
- xAcc[i] = xAccImpact[i];
- yAcc[i] = yAccImpact[i];
- zAcc[i] = zAccImpact[i];
- timestampssOut[i] = timestamps[i];
+ for (int i = 0; i < impacts.nValues; i++) {
+ xAcc[i] = impacts.x[i];
+ yAcc[i] = impacts.y[i];
+ zAcc[i] = impacts.y[i];
+ timestampssOut[i] = impacts.timestamps[i];
}
- *xSize = *ySize = *zSize = totalImpacts;
+ *xSize = *ySize = *zSize = impacts.nValues;
- totalImpacts = 0;
+ impacts.nValues = 0;
- pthread_mutex_unlock(&impactMutex);
+ pthread_mutex_unlock(&impacts.lock);
}
return LE_OK;
}
/*
-*Monitors accelerometer from iio on 100ms intervals
-*Sets hasSuddenImpact flag when accelerometer surpasses threshold
-*/
-void* impactMonitor(void* ptr) {
+ * Monitors accelerometer from iio on 100ms intervals
+ *
+ * We use a context pointer here such that this routine
+ * is not coupled to the global scope. This allows us to pass in
+ * a pointer to a struct that contains the data we care about
+ * instead of storing it globally. Ultimately, the struct we point to
+ * will likely be in the global scope, but this is still a good practice.
+ */
+void* impactMonitor(void* ctx) {
double x, y, z;
le_result_t r = LE_OK;
+ struct suddenImpacts_t* it = ctx;
for (;;) {
brnkl_motion_getCurrentAcceleration(&x, &y, &z);
double impactMagnitude = sqrt(x * x + y * y + z * z);
- if (impactMagnitude > impactThreshold) {
+ if (impactMagnitude > it->threshold) {
// 3. add x, y, z to impact array
- pthread_mutex_lock(&impactMutex);
- r = recordImpact(&x, &y, &z);
- pthread_mutex_unlock(&impactMutex);
+ pthread_mutex_lock(&it->lock);
+ r = recordImpact(it, x, y, z);
+ pthread_mutex_unlock(&it->lock);
}
if (r != LE_OK)
LE_ERROR("Impact Not Recorded");
usleep(SAMPLE_PERIOD_MS * 1000);
}
- return ptr;
+ // should never get here
+ return NULL;
}
/*
-*Create thread to monitor accelerometer iio
-*/
+ *Create thread to monitor accelerometer iio
+ */
void initThread() {
+ pthread_t impactThread;
int thread, mutx;
- LE_INFO("initThread called");
- mutx = pthread_mutex_init(&impactMutex, NULL);
- thread = pthread_create(&impactThread, NULL, impactMonitor, NULL);
- LE_INFO("mutexResult: %d", mutx);
+ mutx = pthread_mutex_init(&impacts.lock, NULL);
+ thread = pthread_create(&impactThread, NULL, impactMonitor, &impacts);
if (thread || mutx) {
LE_ERROR("Reader Thread or Mutex Creation Failed");
} else {