Version FC

Dependencies:   DmTftLibrary eeprom SX1280Lib filesystem mbed

Fork of MSNV2-Terminal_V1-5 by Francis CHATAIN

Service.hpp

Committer:
patrick_duc
Date:
2018-10-19
Branch:
Integration
Revision:
39:13e66d087ae9
Parent:
38:9b43b2415093

File content as of revision 39:13e66d087ae9:

#ifndef __SERVICE_HPP__
#define __SERVICE_HPP__

#include "Context.h"

#ifndef TEST_ENVIRONMENT
#include "mbed.h"
#endif

#include <vector>

#ifdef CPLUSPLUS_99
#include <stdint.h>
#endif

#ifdef TEST_ENVIRONMENT
#include <iostream>
#include <sstream>
#include <string>
#endif

#include "Value.hpp"


namespace misnet {
    class Service;
    class Component;
}


class misnet::Service {
public:

    typedef uint8_t MISNET_CODE;

    enum SERVICE_TYPE {
        SENSOR = 1,
        ACTUATOR = 2,
        RECORDER = 3
    };

    enum REQUEST_MODE {
        SYNCHRONOUS_READ = 1,
        ASYNCHRONOUS_READ = 2,
        STATE_BY_IRQ = 3,
        READ_BY_IRQ = 4
    };

    // A compléter au fur et a mesure et remonter l'info sur les centres applicatifs

    enum DEVICE_ID {
        NOT_IDENTIFIED = 0, //  Configuration nouvelle ou non référencée
        IKS01A2 = 1,        //  Liste des composants
        SMART_TERMINAL = 2  //  BME280 + .... 
    };

    typedef uint8_t GROUP;

    enum STATE {
        ENABLED = 1, //   ACTIVE
        DISABLED = 0 //   ASLEEP
    };

    enum ACCESS_TYPE {
        GPIO_ = 1,
        I2C_ = 2,
        SPI_ = 3,
        UART_ = 4
    };

    typedef uint8_t ACCESS_PIN;

    enum UP_MODE {
        BY_RANGE = 0, // Check whether current value lies within a range
        BY_DELTA = 1, // Check a delta between current value and previous value
        BY_CHANGE = 2 // Check that current value differs from previous value
    };

    /*
    enum REQUEST_MODE {
        IRQ_ = 1, // wakeup by irq
        TIME_ = 2, // wakeup by watchdog timer
    };
     */

    enum ACTION {
        MESSAGE = 1, // Send Message
        MESSAGERELAY = 2 // Send Message + ON/OFF internal relay
    };

    enum OUTPUT_MODE {
        IO = 1, // ON/OFF 
        PWD = 2 // PWD modulation 
    };

    // Constructor
    Service(SERVICE_TYPE type,
            MISNET_CODE misnet_code,
        uint8_t channelNumber,
        misnet::Value::VALUE_TYPE value_type,
            STATE state,
            ACCESS_TYPE access_type,
            REQUEST_MODE request_mode,
            UP_MODE up_mode,
            ACCESS_PIN access_pins[6],
            uint32_t subsample_rate,
            misnet::Value& delta_threshold,
            misnet::Value& low_threshold_limit,
            misnet::Value& high_threshold_limit,
            ACTION action,
            OUTPUT_MODE output_mode,
            std::string comment,
            misnet::Component * parent);

    SERVICE_TYPE getDeviceType() {
        return this->device_type;
    }

    MISNET_CODE getMisnetCode() {
        return this->misnet_code;
    }

    uint8_t getChannelNumber() {
        return this->channel_number;
    }

    misnet::Value::VALUE_TYPE getValueType() {
        return this->value_type;
    }

    STATE getState() {
        return this->state;
    }

    ACCESS_TYPE getAccessType() {
        return this->access_type;
    }

    REQUEST_MODE getRequestMode() {
        return this->request_mode;
    }

    UP_MODE getUpMode() {
        return this->up_mode;
    }

    ACCESS_PIN* getAccessPins() {
        return this->access_pins;
    }

    ACCESS_PIN getAccessPin(short index) {
        return this->access_pins[index - 1];
    }

    uint32_t getSubsampleRate() {
        return this->subsample_rate;
    }

    ACTION getAction() {
        return this->action;
    }

    OUTPUT_MODE getOutputMode() {
        return this->output_mode;
    }

    std::string getComment() {
        return this->comment;
    }

    uint32_t getActivationNb() {
        return this->activation_nb;
    }

    // This method is used to check whether the service is ready to be sampled
    // (ENABLED state and subsampling rate OK)

    bool readyToSample() const {
        return ((this->activation_nb + 1) == this->subsample_rate);
    }

    // This method is used to process a heartbeat : it checks whether the service
    // is ready to be sampled, and updates accordingly the service activation number
    // (reset to 0 if the service is ready ti be sampled, otherwise increments it)
    bool processHeartbeat();

    void incrementActivationNb() {
        ++(this->activation_nb);
    }

    void resetActivationNb() {
        this->activation_nb = 0;
    }

    // This method writes the value passed as argument in the value field of the service.
    // The caller must write the value in "value" field of the srtucture AND set the
    // value of the "type" field of this structure.

    void setValue(misnet::Value& value) {
        this->previous_value = this->current_value;
        this->current_value = value;
    }

    // This other method returns the address of the area where sensor values must be written.
    // The caller must write the value in "value" field of the structure AND set the
    // value of the "type" field of this structure.
    // This method is quicker than the previous one since there is no neeed to copy the value
    // as in the previous method.
    // Drawback : the next method (savePreviousValue) must be called before this one,
    // so that the previous value may be saved. This is necessary when the UP_MODE is BY_RANGE
    // and the delta_threshold field is not empty.

    misnet::Value & getValueAddress() {
        return this->current_value;
    }

    void savePreviousValue() {
        this->previous_value = this->current_value;
    }

    // Check whether current value must be sent to gateway
    bool valueToBeSentToGateway();

#ifdef TEST_ENVIRONMENT
    std::string toString() {
        std::ostringstream stringStream;
        stringStream << "Device type : " << this->device_type
             << ", MISNet code : "
             << (int) this->misnet_code;
        return stringStream.str();
    }
#endif

    // Returns a string representing a value. Used to build messages and to debug.
    // std::string toString(Value& value);

    // Returns a string representing the current value.
#ifdef TEST_ENVIRONMENT
    std::string getCurrentValueAsString() {
        return this->current_value.toString();
    }

    // Returns a string representing the previous value.

    std::string getPreviousValueAsString() {
        return this->previous_value.toString();
    }
#endif

    // Set the delta threshold

    void setDeltaThreshold(misnet::Value delta) {
        this->delta_threshold = delta;
    }

    // Get the delta threshold

    misnet::Value getDeltaThreshold() {
        return this->delta_threshold;
    }

    // Set the low threshold limit

    void setLowThresholdLimit(misnet::Value low_limit) {
        this->low_threshold_limit = low_limit;
    }

    // Get the delta threshold

    misnet::Value getLowThresholdLimit() {
        return this->low_threshold_limit;
    }

    // Set the high threshold limit
    void setHighThresholdLimit(misnet::Value high_limit) {
        this->high_threshold_limit = high_limit;
    }

    // Get the delta threshold
    misnet::Value getHighThresholdLimit() {
        return this->high_threshold_limit;
    }

    // Attempt to read the value of a Service.
    // In case the Service value cannot be read synchronously, start a time that will
    // wait until the value can be read, and place a pointer to the service in the output vector.
    virtual void readValue(std::vector<misnet::Service *>& servicesWithAsynchronousRead) = 0;

    // Read the value of a Service.
    // This method is called for Services which require asynchronous read once the necessary delay has elapsed.
    virtual void readValue() = 0;

    // Get the bitfield representation of service configuration : state, trigger mode, change detection
    uint8_t getConfiguration() {
        uint8_t result = 0;

        if (this->state == misnet::Service::ENABLED) {
            result = 1 << 3;
        }

        switch (this->request_mode) {
            case misnet::Service::READ_BY_IRQ:
            case misnet::Service::STATE_BY_IRQ:
                result += 1 << 2;
                break;
            default:
                break;
        }

        result += this->up_mode & 0x3;

        return result;
    }

protected:
    SERVICE_TYPE device_type;
    MISNET_CODE misnet_code;
    uint8_t channel_number;
    misnet::Value::VALUE_TYPE value_type;
    STATE state;
    ACCESS_TYPE access_type;
    ACCESS_PIN access_pins[6];
    REQUEST_MODE request_mode;
    UP_MODE up_mode;
    uint32_t subsample_rate;
    misnet::Value delta_threshold;
    misnet::Value low_threshold_limit;
    misnet::Value high_threshold_limit;
    ACTION action;
    OUTPUT_MODE output_mode;
    std::string comment;
    misnet::Component * parent;

    uint32_t activation_nb;

    misnet::Value current_value;
    misnet::Value previous_value;
};

#endif // __SERVICE_HPP__