Merge PR #151: New plugin: One-Wire
This commit is contained in:
commit
e98ac4fee5
18
debian/control
vendored
18
debian/control
vendored
@ -13,6 +13,7 @@ Build-depends: libboblight-dev,
|
||||
python:any,
|
||||
qtbase5-dev,
|
||||
qtconnectivity5-dev,
|
||||
libow-dev,
|
||||
Standards-Version: 3.9.3
|
||||
|
||||
|
||||
@ -420,6 +421,22 @@ Description: nymea.io plugin for networkdetector
|
||||
This package will install the nymea.io plugin for networkdetector
|
||||
|
||||
|
||||
|
||||
Package: nymea-plugin-onewire
|
||||
Architecture: any
|
||||
Depends: ${shlibs:Depends},
|
||||
${misc:Depends},
|
||||
nymea-plugins-translations,
|
||||
Description: nymea.io plugin for one wire devices
|
||||
The nymea daemon is a plugin based IoT (Internet of Things) server. The
|
||||
server works like a translator for devices, things and services and
|
||||
allows them to interact.
|
||||
With the powerful rule engine you are able to connect any device available
|
||||
in the system and create individual scenes and behaviors for your environment.
|
||||
.
|
||||
This package will install the nymea.io plugin for one wire devices
|
||||
|
||||
|
||||
Package: nymea-plugin-openweathermap
|
||||
Architecture: any
|
||||
Depends: ${shlibs:Depends},
|
||||
@ -833,6 +850,7 @@ Depends: nymea-plugin-boblight,
|
||||
nymea-plugin-unipi,
|
||||
nymea-plugin-serialportcommander,
|
||||
nymea-plugin-systemmonitor,
|
||||
nymea-plugin-onewire,
|
||||
Replaces: guh-plugins-maker
|
||||
Description: Plugins for nymea IoT server - Meta package for makers, tinkers and hackers
|
||||
The nymea daemon is a plugin based IoT (Internet of Things) server. The
|
||||
|
||||
1
debian/nymea-plugin-onewire.install.in
vendored
Normal file
1
debian/nymea-plugin-onewire.install.in
vendored
Normal file
@ -0,0 +1 @@
|
||||
usr/lib/@DEB_HOST_MULTIARCH@/nymea/plugins/libnymea_devicepluginonewire.so
|
||||
@ -29,6 +29,7 @@ PLUGIN_DIRS = \
|
||||
mqttclient \
|
||||
netatmo \
|
||||
networkdetector \
|
||||
onewire \
|
||||
openweathermap \
|
||||
osdomotics \
|
||||
philipshue \
|
||||
|
||||
39
onewire/README.md
Normal file
39
onewire/README.md
Normal file
@ -0,0 +1,39 @@
|
||||
# One wire
|
||||
|
||||
This plugin allows to add one wire devices through the one wire file system.
|
||||
|
||||
|
||||
## One wire interface device
|
||||
|
||||
This device initializes OWFS, during the device setup you can set OWFS init arguments.
|
||||
Default arguments are "--i2c=ALL:ALL" to scan for one-wire devices on all I2C interfaces.
|
||||
|
||||
You can simulate one-wire device with following init argument: "--fake=10,22,28,05"
|
||||
|
||||
More about init arguments here: https://www.owfs.org
|
||||
|
||||
## Supported one-wire devices
|
||||
|
||||
* Family Code 10 - Temperature Sensors
|
||||
..* DS18S20
|
||||
..* DS1820
|
||||
..* DS18S20-PAR
|
||||
..* DS1920
|
||||
* Family Code 22 - Temperature Sensors
|
||||
..* DS1822
|
||||
..* DS1822-PAR
|
||||
* Family Code 28 - Temperature Sensors
|
||||
..* DS18B20
|
||||
..* DS18B20-PAR
|
||||
..* DS18B20X
|
||||
* Family Code 3B - Temperature Sensors
|
||||
..* DS1825
|
||||
* Family Code 05 - Single channel switch
|
||||
..* DS2405
|
||||
* Family Code 12 - Dual channel switch
|
||||
..* DS2406
|
||||
..* DS2407
|
||||
* Family Code 3A - Dual channel switch
|
||||
..* DS2413
|
||||
* Family Code 29 - Eight channel switch
|
||||
..* DS2408
|
||||
374
onewire/devicepluginonewire.cpp
Normal file
374
onewire/devicepluginonewire.cpp
Normal file
@ -0,0 +1,374 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2018 Bernhard Trinnes <bernhard.trinnes@nymea.io> *
|
||||
* *
|
||||
* This file is part of nymea. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Lesser General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2.1 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* Lesser General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Lesser General Public *
|
||||
* License along with this library; If not, see *
|
||||
* <http://www.gnu.org/licenses/>. *
|
||||
* *
|
||||
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||
|
||||
|
||||
|
||||
#include "devicepluginonewire.h"
|
||||
#include "devices/device.h"
|
||||
#include "plugininfo.h"
|
||||
|
||||
#include <QDebug>
|
||||
#include <QDir>
|
||||
|
||||
DevicePluginOneWire::DevicePluginOneWire()
|
||||
{
|
||||
}
|
||||
|
||||
Device::DeviceError DevicePluginOneWire::discoverDevices(const DeviceClassId &deviceClassId, const ParamList ¶ms)
|
||||
{
|
||||
Q_UNUSED(params);
|
||||
|
||||
if (deviceClassId == temperatureSensorDeviceClassId ||
|
||||
deviceClassId == singleChannelSwitchDeviceClassId ||
|
||||
deviceClassId == dualChannelSwitchDeviceClassId ||
|
||||
deviceClassId == eightChannelSwitchDeviceClassId) {
|
||||
|
||||
if (myDevices().filterByDeviceClassId(oneWireInterfaceDeviceClassId).isEmpty()) {
|
||||
//No one wire interface intitialized
|
||||
return Device::DeviceErrorHardwareNotAvailable;
|
||||
}
|
||||
|
||||
foreach(Device *parentDevice, myDevices().filterByDeviceClassId(oneWireInterfaceDeviceClassId)) {
|
||||
if (parentDevice->stateValue(oneWireInterfaceAutoAddStateTypeId).toBool()) {
|
||||
//devices cannot be discovered since auto mode is enabled
|
||||
return Device::DeviceErrorNoError;
|
||||
} else {
|
||||
if (m_oneWireInterface)
|
||||
m_oneWireInterface->discoverDevices();
|
||||
}
|
||||
}
|
||||
return Device::DeviceErrorAsync;
|
||||
}
|
||||
return Device::DeviceErrorDeviceClassNotFound;
|
||||
}
|
||||
|
||||
|
||||
Device::DeviceSetupStatus DevicePluginOneWire::setupDevice(Device *device)
|
||||
{
|
||||
if (device->deviceClassId() == oneWireInterfaceDeviceClassId) {
|
||||
qCDebug(dcOneWire) << "Setup one wire interface";
|
||||
|
||||
if (m_oneWireInterface) {
|
||||
qCWarning(dcOneWire) << "One wire interface already set up";
|
||||
return Device::DeviceSetupStatusFailure;
|
||||
}
|
||||
m_oneWireInterface = new OneWire(this);
|
||||
QByteArray initArguments = device->paramValue(oneWireInterfaceDeviceInitArgsParamTypeId).toByteArray();
|
||||
|
||||
if (!m_oneWireInterface->init(initArguments)){
|
||||
m_oneWireInterface->deleteLater();
|
||||
m_oneWireInterface = nullptr;
|
||||
return Device::DeviceSetupStatusFailure;
|
||||
}
|
||||
connect(m_oneWireInterface, &OneWire::devicesDiscovered, this, &DevicePluginOneWire::onOneWireDevicesDiscovered);
|
||||
return Device::DeviceSetupStatusSuccess;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == temperatureSensorDeviceClassId) {
|
||||
|
||||
qCDebug(dcOneWire) << "Setup one wire temperature sensor" << device->params();
|
||||
if (!m_oneWireInterface) { //in case the child was setup before the interface
|
||||
double temperature = m_oneWireInterface->getTemperature(device->paramValue(temperatureSensorDeviceAddressParamTypeId).toByteArray());
|
||||
device->setStateValue(temperatureSensorTemperatureStateTypeId, temperature);
|
||||
}
|
||||
return Device::DeviceSetupStatusSuccess;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == singleChannelSwitchDeviceClassId) {
|
||||
qCDebug(dcOneWire) << "Setup one wire switch" << device->params();
|
||||
if (!m_oneWireInterface) {
|
||||
QByteArray address = device->paramValue(singleChannelSwitchDeviceAddressParamTypeId).toByteArray();
|
||||
device->setStateValue(singleChannelSwitchDigitalOutputStateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_A));
|
||||
}
|
||||
return Device::DeviceSetupStatusSuccess;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == dualChannelSwitchDeviceClassId) {
|
||||
qCDebug(dcOneWire) << "Setup one wire dual switch" << device->params();
|
||||
if (!m_oneWireInterface) {
|
||||
QByteArray address = device->paramValue(dualChannelSwitchDeviceAddressParamTypeId).toByteArray();
|
||||
device->setStateValue(dualChannelSwitchDigitalOutput1StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_A));
|
||||
device->setStateValue(dualChannelSwitchDigitalOutput2StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_B));
|
||||
}
|
||||
return Device::DeviceSetupStatusSuccess;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == eightChannelSwitchDeviceClassId) {
|
||||
qCDebug(dcOneWire) << "Setup one wire eight channel switch" << device->params();
|
||||
if (!m_oneWireInterface) {
|
||||
QByteArray address = device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray();
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput1StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_A));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput2StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_B));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput3StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_C));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput4StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_D));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput5StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_E));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput6StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_F));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput7StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_G));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput8StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_H));
|
||||
}
|
||||
return Device::DeviceSetupStatusSuccess;
|
||||
}
|
||||
return Device::DeviceSetupStatusFailure;
|
||||
}
|
||||
|
||||
void DevicePluginOneWire::postSetupDevice(Device *device)
|
||||
{
|
||||
Q_UNUSED(device);
|
||||
|
||||
if(!m_pluginTimer) {
|
||||
m_pluginTimer = hardwareManager()->pluginTimerManager()->registerTimer(10);
|
||||
connect(m_pluginTimer, &PluginTimer::timeout, this, &DevicePluginOneWire::onPluginTimer);
|
||||
}
|
||||
}
|
||||
|
||||
Device::DeviceError DevicePluginOneWire::executeAction(Device *device, const Action &action)
|
||||
{
|
||||
if (device->deviceClassId() == oneWireInterfaceDeviceClassId) {
|
||||
if (action.actionTypeId() == oneWireInterfaceAutoAddActionTypeId){
|
||||
device->setStateValue(oneWireInterfaceAutoAddStateTypeId, action.param(oneWireInterfaceAutoAddActionAutoAddParamTypeId).value());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
return Device::DeviceErrorActionTypeNotFound;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == singleChannelSwitchDeviceClassId) {
|
||||
if (action.actionTypeId() == singleChannelSwitchDigitalOutputActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(singleChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_A, action.param(singleChannelSwitchDigitalOutputActionDigitalOutputParamTypeId).value().toBool());
|
||||
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
return Device::DeviceErrorActionTypeNotFound;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == dualChannelSwitchDeviceClassId) {
|
||||
if (action.actionTypeId() == dualChannelSwitchDigitalOutput1ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(dualChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_A, action.param(dualChannelSwitchDigitalOutput1ActionDigitalOutput1ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == dualChannelSwitchDigitalOutput2ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(dualChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_B, action.param(dualChannelSwitchDigitalOutput2ActionDigitalOutput2ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
return Device::DeviceErrorActionTypeNotFound;
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == eightChannelSwitchDeviceClassId) {
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput1ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_A, action.param(eightChannelSwitchDigitalOutput1ActionDigitalOutput1ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput2ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_B, action.param(eightChannelSwitchDigitalOutput2ActionDigitalOutput2ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput3ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_C, action.param(eightChannelSwitchDigitalOutput3ActionDigitalOutput3ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput4ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_D, action.param(eightChannelSwitchDigitalOutput4ActionDigitalOutput4ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput5ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_E, action.param(eightChannelSwitchDigitalOutput5ActionDigitalOutput5ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput6ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_F, action.param(eightChannelSwitchDigitalOutput6ActionDigitalOutput6ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput7ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_G, action.param(eightChannelSwitchDigitalOutput7ActionDigitalOutput7ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
if (action.actionTypeId() == eightChannelSwitchDigitalOutput8ActionTypeId){
|
||||
m_oneWireInterface->setSwitchOutput(device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray(), OneWire::SwitchChannel::PIO_H, action.param(eightChannelSwitchDigitalOutput8ActionDigitalOutput8ParamTypeId).value().toBool());
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
return Device::DeviceErrorActionTypeNotFound;
|
||||
}
|
||||
return Device::DeviceErrorNoError;
|
||||
}
|
||||
|
||||
|
||||
void DevicePluginOneWire::deviceRemoved(Device *device)
|
||||
{
|
||||
if (device->deviceClassId() == oneWireInterfaceDeviceClassId) {
|
||||
m_oneWireInterface->deleteLater();
|
||||
m_oneWireInterface = nullptr;
|
||||
return;
|
||||
}
|
||||
|
||||
if (myDevices().empty()) {
|
||||
hardwareManager()->pluginTimerManager()->unregisterTimer(m_pluginTimer);
|
||||
m_pluginTimer = nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void DevicePluginOneWire::onPluginTimer()
|
||||
{
|
||||
foreach (Device *device, myDevices()) {
|
||||
if (device->deviceClassId() == oneWireInterfaceDeviceClassId) {
|
||||
device->setStateValue(oneWireInterfaceConnectedStateTypeId, m_oneWireInterface->interfaceIsAvailable());
|
||||
|
||||
if (device->stateValue(oneWireInterfaceAutoAddStateTypeId).toBool()) {
|
||||
m_oneWireInterface->discoverDevices();
|
||||
}
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == temperatureSensorDeviceClassId) {
|
||||
QByteArray address = device->paramValue(temperatureSensorDeviceAddressParamTypeId).toByteArray();
|
||||
|
||||
double temperature = m_oneWireInterface->getTemperature(address);
|
||||
device->setStateValue(temperatureSensorTemperatureStateTypeId, temperature);
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == singleChannelSwitchDeviceClassId) {
|
||||
QByteArray address = device->paramValue(singleChannelSwitchDeviceAddressParamTypeId).toByteArray();
|
||||
device->setStateValue(singleChannelSwitchDigitalOutputStateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_A));
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == dualChannelSwitchDeviceClassId) {
|
||||
QByteArray address = device->paramValue(dualChannelSwitchDeviceAddressParamTypeId).toByteArray();
|
||||
device->setStateValue(dualChannelSwitchDigitalOutput1StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_A));
|
||||
device->setStateValue(dualChannelSwitchDigitalOutput2StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_B));
|
||||
}
|
||||
|
||||
if (device->deviceClassId() == eightChannelSwitchDeviceClassId) {
|
||||
QByteArray address = device->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toByteArray();
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput1StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_A));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput2StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_B));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput3StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_C));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput4StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_D));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput5StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_E));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput6StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_F));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput7StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_G));
|
||||
device->setStateValue(eightChannelSwitchDigitalOutput8StateTypeId, m_oneWireInterface->getSwitchOutput(address, OneWire::SwitchChannel::PIO_H));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void DevicePluginOneWire::onOneWireDevicesDiscovered(QList<OneWire::OneWireDevice> oneWireDevices)
|
||||
{
|
||||
foreach(Device *parentDevice, myDevices().filterByDeviceClassId(oneWireInterfaceDeviceClassId)) {
|
||||
|
||||
bool autoDiscoverEnabled = parentDevice->stateValue(oneWireInterfaceAutoAddStateTypeId).toBool();
|
||||
QList<DeviceDescriptor> temperatureDeviceDescriptors;
|
||||
QList<DeviceDescriptor> singleChannelSwitchDeviceDescriptors;
|
||||
QList<DeviceDescriptor> dualChannelSwitchDeviceDescriptors;
|
||||
QList<DeviceDescriptor> eightChannelSwitchDeviceDescriptors;
|
||||
foreach (OneWire::OneWireDevice oneWireDevice, oneWireDevices){
|
||||
switch (oneWireDevice.family) {
|
||||
//https://github.com/owfs/owfs-doc/wiki/1Wire-Device-List
|
||||
case 0x10: //DS18S20
|
||||
case 0x22: //DS1822
|
||||
case 0x28: //DS18B20
|
||||
case 0x3b: {//DS1825, MAX31826, MAX31850
|
||||
DeviceDescriptor descriptor(temperatureSensorDeviceClassId, oneWireDevice.type, "One wire temperature sensor", parentDevice->id());
|
||||
ParamList params;
|
||||
params.append(Param(temperatureSensorDeviceAddressParamTypeId, oneWireDevice.address));
|
||||
params.append(Param(temperatureSensorDeviceTypeParamTypeId, oneWireDevice.type));
|
||||
foreach (Device *existingDevice, myDevices().filterByDeviceClassId(temperatureSensorDeviceClassId)){
|
||||
if (existingDevice->paramValue(temperatureSensorDeviceAddressParamTypeId).toString() == oneWireDevice.address) {
|
||||
descriptor.setDeviceId(existingDevice->id());
|
||||
break;
|
||||
}
|
||||
}
|
||||
descriptor.setParams(params);
|
||||
temperatureDeviceDescriptors.append(descriptor);
|
||||
break;
|
||||
}
|
||||
case 0x05: { //single channel switch
|
||||
DeviceDescriptor descriptor(singleChannelSwitchDeviceClassId, oneWireDevice.type, "One wire single channel switch", parentDevice->id());
|
||||
ParamList params;
|
||||
params.append(Param(singleChannelSwitchDeviceAddressParamTypeId, oneWireDevice.address));
|
||||
params.append(Param(singleChannelSwitchDeviceTypeParamTypeId, oneWireDevice.type));
|
||||
foreach (Device *existingDevice, myDevices().filterByDeviceClassId(singleChannelSwitchDeviceClassId)){
|
||||
if (existingDevice->paramValue(singleChannelSwitchDeviceAddressParamTypeId).toString() == oneWireDevice.address) {
|
||||
descriptor.setDeviceId(existingDevice->id());
|
||||
break;
|
||||
}
|
||||
}
|
||||
descriptor.setParams(params);
|
||||
singleChannelSwitchDeviceDescriptors.append(descriptor);
|
||||
break;
|
||||
}
|
||||
case 0x12:
|
||||
case 0x3a: {//dual channel switch
|
||||
DeviceDescriptor descriptor(dualChannelSwitchDeviceClassId, oneWireDevice.type, "One wire dual channel switch", parentDevice->id());
|
||||
ParamList params;
|
||||
params.append(Param(dualChannelSwitchDeviceAddressParamTypeId, oneWireDevice.address));
|
||||
params.append(Param(dualChannelSwitchDeviceTypeParamTypeId, oneWireDevice.type));
|
||||
foreach (Device *existingDevice, myDevices().filterByDeviceClassId(dualChannelSwitchDeviceClassId)){
|
||||
if (existingDevice->paramValue(dualChannelSwitchDeviceAddressParamTypeId).toString() == oneWireDevice.address) {
|
||||
descriptor.setDeviceId(existingDevice->id());
|
||||
break;
|
||||
}
|
||||
}
|
||||
descriptor.setParams(params);
|
||||
dualChannelSwitchDeviceDescriptors.append(descriptor);
|
||||
break;
|
||||
}
|
||||
case 0x29: { //eight channel switch
|
||||
DeviceDescriptor descriptor(eightChannelSwitchDeviceClassId, oneWireDevice.type, "One wire eight channel switch", parentDevice->id());
|
||||
ParamList params;
|
||||
params.append(Param(eightChannelSwitchDeviceAddressParamTypeId, oneWireDevice.address));
|
||||
params.append(Param(eightChannelSwitchDeviceTypeParamTypeId, oneWireDevice.type));
|
||||
foreach (Device *existingDevice, myDevices().filterByDeviceClassId(eightChannelSwitchDeviceClassId)){
|
||||
if (existingDevice->paramValue(eightChannelSwitchDeviceAddressParamTypeId).toString() == oneWireDevice.address) {
|
||||
descriptor.setDeviceId(existingDevice->id());
|
||||
break;
|
||||
}
|
||||
}
|
||||
descriptor.setParams(params);
|
||||
eightChannelSwitchDeviceDescriptors.append(descriptor);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
qDebug(dcOneWire()) << "Unknown Device discovered" << oneWireDevice.type << oneWireDevice.address;
|
||||
break;
|
||||
|
||||
}
|
||||
}
|
||||
if (autoDiscoverEnabled) {
|
||||
if (!temperatureDeviceDescriptors.isEmpty())
|
||||
emit autoDevicesAppeared(temperatureSensorDeviceClassId, temperatureDeviceDescriptors);
|
||||
if (!singleChannelSwitchDeviceDescriptors.isEmpty())
|
||||
emit autoDevicesAppeared(singleChannelSwitchDeviceClassId, singleChannelSwitchDeviceDescriptors);
|
||||
if (!dualChannelSwitchDeviceDescriptors.isEmpty())
|
||||
emit autoDevicesAppeared(dualChannelSwitchDeviceClassId, dualChannelSwitchDeviceDescriptors);
|
||||
if (!eightChannelSwitchDeviceDescriptors.isEmpty())
|
||||
emit autoDevicesAppeared(eightChannelSwitchDeviceClassId, eightChannelSwitchDeviceDescriptors);
|
||||
} else {
|
||||
if (!temperatureDeviceDescriptors.isEmpty())
|
||||
emit devicesDiscovered(temperatureSensorDeviceClassId, temperatureDeviceDescriptors);
|
||||
if (!singleChannelSwitchDeviceDescriptors.isEmpty())
|
||||
emit devicesDiscovered(singleChannelSwitchDeviceClassId, singleChannelSwitchDeviceDescriptors);
|
||||
if (!dualChannelSwitchDeviceDescriptors.isEmpty())
|
||||
emit devicesDiscovered(dualChannelSwitchDeviceClassId, dualChannelSwitchDeviceDescriptors);
|
||||
if (!eightChannelSwitchDeviceDescriptors.isEmpty())
|
||||
emit devicesDiscovered(eightChannelSwitchDeviceClassId, eightChannelSwitchDeviceDescriptors);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
56
onewire/devicepluginonewire.h
Normal file
56
onewire/devicepluginonewire.h
Normal file
@ -0,0 +1,56 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2018 Bernhard Trinnes <bernhard.trinnes@guh.io> *
|
||||
* *
|
||||
* This file is part of nymea. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Lesser General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2.1 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* Lesser General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Lesser General Public *
|
||||
* License along with this library; If not, see *
|
||||
* <http://www.gnu.org/licenses/>. *
|
||||
* *
|
||||
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||
|
||||
#ifndef DEVICEPLUGINONEWIRE_H
|
||||
#define DEVICEPLUGINONEWIRE_H
|
||||
|
||||
#include "plugintimer.h"
|
||||
#include "devices/deviceplugin.h"
|
||||
#include "onewire.h"
|
||||
|
||||
#include <QHash>
|
||||
|
||||
class DevicePluginOneWire : public DevicePlugin
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PLUGIN_METADATA(IID "io.nymea.DevicePlugin" FILE "devicepluginonewire.json")
|
||||
Q_INTERFACES(DevicePlugin)
|
||||
|
||||
public:
|
||||
explicit DevicePluginOneWire();
|
||||
|
||||
Device::DeviceError discoverDevices(const DeviceClassId &deviceClassId, const ParamList ¶ms) override;
|
||||
Device::DeviceSetupStatus setupDevice(Device *device) override;
|
||||
void postSetupDevice(Device *device) override;
|
||||
Device::DeviceError executeAction(Device *device, const Action &action) override;
|
||||
void deviceRemoved(Device *device) override;
|
||||
|
||||
private:
|
||||
PluginTimer *m_pluginTimer = nullptr;
|
||||
OneWire *m_oneWireInterface = nullptr;
|
||||
|
||||
private slots:
|
||||
void onPluginTimer();
|
||||
void onOneWireDevicesDiscovered(QList<OneWire::OneWireDevice> devices);
|
||||
};
|
||||
|
||||
#endif // DEVICEPLUGINONEWIRE_H
|
||||
274
onewire/devicepluginonewire.json
Normal file
274
onewire/devicepluginonewire.json
Normal file
@ -0,0 +1,274 @@
|
||||
{
|
||||
"displayName": "One Wire",
|
||||
"name": "OneWire",
|
||||
"id": "2c697fb7-0645-466d-9cb9-aa1922c85bee",
|
||||
"vendors": [
|
||||
{
|
||||
"displayName": "One wire",
|
||||
"name": "oneWire",
|
||||
"id": "cecc5fae-29cf-40c0-b1f8-0af2dc8e8a63",
|
||||
"deviceClasses": [
|
||||
{
|
||||
"id": "c36c68d9-6182-4ae1-972d-b8b5e0cf185f",
|
||||
"name": "oneWireInterface",
|
||||
"displayName": "One wire interface",
|
||||
"interfaces": ["gateway"],
|
||||
"createMethods": ["user"],
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "a0e773ff-fd19-499e-96f0-830168229cd3",
|
||||
"name": "initArgs",
|
||||
"displayName": "OWFS init arguments",
|
||||
"type": "QString",
|
||||
"defaultValue": "--i2c=ALL:ALL"
|
||||
}
|
||||
],
|
||||
"stateTypes": [
|
||||
{
|
||||
"id": "d0ded173-c382-4ee3-8e24-3647b4e16afa",
|
||||
"name": "connected",
|
||||
"displayName": "connected",
|
||||
"displayNameEvent": "connected changed",
|
||||
"defaultValue": false,
|
||||
"type": "bool"
|
||||
},
|
||||
{
|
||||
"id": "64baf50e-8ed4-4526-8b92-7e4662d6fa39",
|
||||
"name": "autoAdd",
|
||||
"displayName": "Auto add one wire devices",
|
||||
"displayNameAction": "Set auto add mode",
|
||||
"displayNameEvent": "Auto add one wire devices changed",
|
||||
"defaultValue": false,
|
||||
"type": "bool",
|
||||
"writable": true
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "e13beb24-953c-48b3-9262-7cde31d42ef5",
|
||||
"name": "temperatureSensor",
|
||||
"displayName": "Temperature Sensor",
|
||||
"interfaces": ["temperaturesensor"],
|
||||
"createMethods": ["discovery"],
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "b4368f34-d9bb-496f-84ba-091bd4b6a332",
|
||||
"name": "address",
|
||||
"displayName": "Address",
|
||||
"type": "QString",
|
||||
"readOnly": true
|
||||
},
|
||||
{
|
||||
"id": "5005822d-6a32-4bb8-9b77-f79da7382f76",
|
||||
"name": "type",
|
||||
"displayName": "Type",
|
||||
"type": "QString",
|
||||
"inputType": "TextLine",
|
||||
"readOnly": true
|
||||
}
|
||||
],
|
||||
"stateTypes": [
|
||||
{
|
||||
"id": "b04ee2a5-9b27-4ffc-9e12-7e05f5a41690",
|
||||
"name": "temperature",
|
||||
"displayName": "temperature",
|
||||
"displayNameEvent": "temperature changed",
|
||||
"unit": "DegreeCelsius",
|
||||
"type": "double",
|
||||
"defaultValue": 0
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "6db42501-5451-4aac-9525-5f886b3188e2",
|
||||
"name": "singleChannelSwitch",
|
||||
"displayName": "1-channel switch",
|
||||
"interfaces": [ ],
|
||||
"createMethods": ["discovery"],
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "c9d6b7fd-fa21-473a-b5ed-9c5227749f06",
|
||||
"name": "address",
|
||||
"displayName": "Address",
|
||||
"type": "QString",
|
||||
"readOnly": true
|
||||
},
|
||||
{
|
||||
"id": "6efc8cb6-81ae-45c0-8910-708401d1ba68",
|
||||
"name": "type",
|
||||
"displayName": "Type",
|
||||
"type": "QString",
|
||||
"inputType": "TextLine",
|
||||
"readOnly": true
|
||||
}
|
||||
],
|
||||
"stateTypes": [
|
||||
{
|
||||
"id": "ca10a9fd-e4e0-4608-a2d2-6a4ce9644f40",
|
||||
"name": "digitalOutput",
|
||||
"displayName": "Digital output",
|
||||
"displayNameEvent": "Digital output changed",
|
||||
"displayNameAction": "Set digital output",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "023f2b93-61e1-4422-97f5-3d5c14a6628f",
|
||||
"name": "dualChannelSwitch",
|
||||
"displayName": "2-channel switch",
|
||||
"interfaces": [ ],
|
||||
"createMethods": ["discovery"],
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "b9a1a23d-1fbf-4849-8aa2-2855e7deaf84",
|
||||
"name": "address",
|
||||
"displayName": "Address",
|
||||
"type": "QString",
|
||||
"readOnly": true
|
||||
},
|
||||
{
|
||||
"id": "b71ed57b-e768-4119-829e-a0f2c9fa5e18",
|
||||
"name": "type",
|
||||
"displayName": "Type",
|
||||
"type": "QString",
|
||||
"inputType": "TextLine",
|
||||
"readOnly": true
|
||||
}
|
||||
],
|
||||
"stateTypes": [
|
||||
{
|
||||
"id": "f8b6b4a7-355c-4580-a676-8a4d0d619ff9",
|
||||
"name": "digitalOutput1",
|
||||
"displayName": "Digital output 1",
|
||||
"displayNameEvent": "Digital output 1 changed",
|
||||
"displayNameAction": "Set digital output 1",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "82a78aed-5994-4af5-aecb-1806be5de1f3",
|
||||
"name": "digitalOutput2",
|
||||
"displayName": "Digital output 2",
|
||||
"displayNameEvent": "Digital output 2 changed",
|
||||
"displayNameAction": "Set digital output 2",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "71691119-3bda-4424-b853-1a00f21086e1",
|
||||
"name": "eightChannelSwitch",
|
||||
"displayName": "8-channel switch",
|
||||
"interfaces": [ ],
|
||||
"createMethods": ["discovery"],
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "e3e6e596-0cd4-42a3-8401-ccf6349314b7",
|
||||
"name": "address",
|
||||
"displayName": "Address",
|
||||
"type": "QString",
|
||||
"readOnly": true
|
||||
},
|
||||
{
|
||||
"id": "34c8f771-4141-4183-9eaf-becbaf362ac8",
|
||||
"name": "type",
|
||||
"displayName": "Type",
|
||||
"type": "QString",
|
||||
"inputType": "TextLine",
|
||||
"readOnly": true
|
||||
}
|
||||
],
|
||||
"stateTypes": [
|
||||
{
|
||||
"id": "78fa12c0-246c-4112-8be6-5943d3c3cda5",
|
||||
"name": "digitalOutput1",
|
||||
"displayName": "Digital output 1",
|
||||
"displayNameEvent": "Digital output 1 changed",
|
||||
"displayNameAction": "Set digital output 1",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "c7d2f4a8-2b13-4a48-81a8-72f4908c775b",
|
||||
"name": "digitalOutput2",
|
||||
"displayName": "Digital output 2",
|
||||
"displayNameEvent": "Digital output 2 changed",
|
||||
"displayNameAction": "Set digital output 2",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "4b2ac595-eba9-4364-8cd7-00ff8bccda5a",
|
||||
"name": "digitalOutput3",
|
||||
"displayName": "Digital output 3",
|
||||
"displayNameEvent": "Digital output 3 changed",
|
||||
"displayNameAction": "Set digital output 3",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "bbbd1863-ef04-4687-803d-3c9ccdfc8d8f",
|
||||
"name": "digitalOutput4",
|
||||
"displayName": "Digital output 4",
|
||||
"displayNameEvent": "Digital output 4 changed",
|
||||
"displayNameAction": "Set digital output 4",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "50855d2b-a700-4030-8674-fee00cc0b4e2",
|
||||
"name": "digitalOutput5",
|
||||
"displayName": "Digital output 5",
|
||||
"displayNameEvent": "Digital output 5 changed",
|
||||
"displayNameAction": "Set digital output 5",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "a91ce593-09ba-4754-8a2e-e3f507313585",
|
||||
"name": "digitalOutput6",
|
||||
"displayName": "Digital output 6",
|
||||
"displayNameEvent": "Digital output 6 changed",
|
||||
"displayNameAction": "Set digital output 6",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "5f46047c-b00d-486f-b169-b738fbc89cdb",
|
||||
"name": "digitalOutput7",
|
||||
"displayName": "Digital output 7",
|
||||
"displayNameEvent": "Digital output 7 changed",
|
||||
"displayNameAction": "Set digital output 7",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
},
|
||||
{
|
||||
"id": "63334a17-0847-4f53-8007-1b5e72b88aa8",
|
||||
"name": "digitalOutput8",
|
||||
"displayName": "Digital output 8",
|
||||
"displayNameEvent": "Digital output 8 changed",
|
||||
"displayNameAction": "Set digital output 8",
|
||||
"type": "bool",
|
||||
"defaultValue": false,
|
||||
"writable": true
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
280
onewire/onewire.cpp
Normal file
280
onewire/onewire.cpp
Normal file
@ -0,0 +1,280 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2018 Bernhard Trinnes <bernhard.trinnes@guh.io> *
|
||||
* *
|
||||
* This file is part of nymea. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Lesser General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2.1 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* Lesser General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Lesser General Public *
|
||||
* License along with this library; If not, see *
|
||||
* <http://www.gnu.org/licenses/>. *
|
||||
* *
|
||||
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||
|
||||
#include "onewire.h"
|
||||
#include "extern-plugininfo.h"
|
||||
|
||||
OneWire::OneWire(QObject *parent) :
|
||||
QObject(parent)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
OneWire::~OneWire()
|
||||
{
|
||||
OW_finish();
|
||||
}
|
||||
|
||||
bool OneWire::init(const QByteArray &owfsInitArguments)
|
||||
{
|
||||
//QByteArray initArguments;
|
||||
//Test OWFS arguments
|
||||
//initArguments.append("--fake 28 --fake 10"); //fake temperature sensors
|
||||
//initArguments.append("--fake 29 --fake 12 --fake 05"); //fake temperature sensor
|
||||
|
||||
//Test i2c
|
||||
//initArguments.append("--i2c=ALL:ALL");
|
||||
|
||||
if (OW_init(owfsInitArguments) < 0) {
|
||||
qWarning(dcOneWire()) << "ERROR initialising one wire" << strerror(errno);
|
||||
return false;
|
||||
}
|
||||
m_path = "/";
|
||||
return true;
|
||||
}
|
||||
|
||||
bool OneWire::discoverDevices()
|
||||
{
|
||||
char *dirBuffer = nullptr;
|
||||
size_t dirLength ;
|
||||
|
||||
if (OW_get(m_path, &dirBuffer, &dirLength) < 0) {
|
||||
qWarning(dcOneWire()) << "DIRECTORY ERROR" << strerror(errno);
|
||||
return false;
|
||||
}
|
||||
qDebug(dcOneWire()) << "Directory has members" << dirBuffer;
|
||||
|
||||
QList<QByteArray> dirMembers ;
|
||||
dirMembers = QByteArray(dirBuffer, dirLength).split(',');
|
||||
free(dirBuffer);
|
||||
|
||||
QList<OneWireDevice> oneWireDevices;
|
||||
foreach(QByteArray member, dirMembers) {
|
||||
|
||||
/* Other system members:
|
||||
* bus.0
|
||||
* uncached
|
||||
* settings
|
||||
* system
|
||||
* statistics
|
||||
* structure
|
||||
* simultaneous
|
||||
* alarm
|
||||
*/
|
||||
|
||||
int family = member.split('.').first().toInt(nullptr, 16);
|
||||
if (family != 0) {
|
||||
member.remove(member.indexOf('/'), 1);
|
||||
QByteArray type;
|
||||
OneWireDevice device;
|
||||
device.family = family;
|
||||
device.address = member;
|
||||
device.id = member.split('.').last();
|
||||
device.type = getValue(member, "type");
|
||||
oneWireDevices.append(device);
|
||||
}
|
||||
}
|
||||
if(!oneWireDevices.isEmpty()) {
|
||||
emit devicesDiscovered(oneWireDevices);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool OneWire::interfaceIsAvailable()
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
bool OneWire::isConnected(const QByteArray &address)
|
||||
{
|
||||
Q_UNUSED(address)
|
||||
QByteArray fullPath;
|
||||
fullPath.append(m_path);
|
||||
fullPath.append(address);
|
||||
fullPath.append('\0');
|
||||
if(OW_present(fullPath) < 0)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
/* Takes a path and filename and prints the 1-wire value */
|
||||
/* makes sure the bridging "/" in the path is correct */
|
||||
/* watches for total length and free allocated space */
|
||||
QByteArray OneWire::getValue(const QByteArray &address, const QByteArray &type)
|
||||
{
|
||||
char * getBuffer ;
|
||||
size_t getLength ;
|
||||
|
||||
QByteArray devicePath;
|
||||
devicePath.append(m_path);
|
||||
if(!m_path.endsWith('/'))
|
||||
devicePath.append('/');
|
||||
devicePath.append(address);
|
||||
devicePath.append('/');
|
||||
devicePath.append(type);
|
||||
devicePath.append('\0');
|
||||
|
||||
if (OW_get(devicePath, &getBuffer, &getLength) < 0) {
|
||||
qWarning(dcOneWire()) << "ERROR reading" << devicePath << strerror(errno);
|
||||
}
|
||||
|
||||
qDebug(dcOneWire()) << "Device value" << devicePath << getBuffer;
|
||||
|
||||
QByteArray value = QByteArray(getBuffer, getLength);
|
||||
free(getBuffer);
|
||||
return value;
|
||||
}
|
||||
|
||||
void OneWire::setValue(const QByteArray &address, const QByteArray &type, const QByteArray &value)
|
||||
{
|
||||
Q_UNUSED(value)
|
||||
QByteArray devicePath;
|
||||
devicePath.append(m_path);
|
||||
if(!m_path.endsWith('/'))
|
||||
devicePath.append('/');
|
||||
devicePath.append(address);
|
||||
devicePath.append('/');
|
||||
devicePath.append(type);
|
||||
devicePath.append('\0');
|
||||
|
||||
if (OW_put(devicePath, value, value.length()) < 0) {
|
||||
qWarning(dcOneWire()) << "ERROR reading" << devicePath << strerror(errno);
|
||||
}
|
||||
}
|
||||
|
||||
double OneWire::getTemperature(const QByteArray &address)
|
||||
{
|
||||
QByteArray temperature = getValue(address, "temperature");
|
||||
qDebug(dcOneWire()) << "Temperature" << temperature << temperature.replace(',','.').toDouble();
|
||||
return temperature.toDouble();
|
||||
}
|
||||
|
||||
QByteArray OneWire::getType(const QByteArray &address)
|
||||
{
|
||||
QByteArray type = getValue(address, "type");
|
||||
return type;
|
||||
}
|
||||
|
||||
bool OneWire::getSwitchOutput(const QByteArray &address, SwitchChannel channel)
|
||||
{
|
||||
QByteArray c;
|
||||
c.append("PIO.");
|
||||
switch (channel) {
|
||||
case PIO_A:
|
||||
c.append('A');
|
||||
break;
|
||||
case PIO_B:
|
||||
c.append('B');
|
||||
break;
|
||||
case PIO_C:
|
||||
c.append('C');
|
||||
break;
|
||||
case PIO_D:
|
||||
c.append('D');
|
||||
break;
|
||||
case PIO_E:
|
||||
c.append('E');
|
||||
break;
|
||||
case PIO_F:
|
||||
c.append('F');
|
||||
break;
|
||||
case PIO_G:
|
||||
c.append('G');
|
||||
break;
|
||||
case PIO_H:
|
||||
c.append('H');
|
||||
break;
|
||||
}
|
||||
QByteArray state = getValue(address, c);
|
||||
qDebug(dcOneWire()) << "Switch state" << state.toInt();
|
||||
return state.toInt();
|
||||
}
|
||||
|
||||
bool OneWire::getSwitchInput(const QByteArray &address, SwitchChannel channel)
|
||||
{
|
||||
QByteArray c;
|
||||
c.append("sensed.");
|
||||
switch (channel) {
|
||||
case PIO_A:
|
||||
c.append('A');
|
||||
break;
|
||||
case PIO_B:
|
||||
c.append('B');
|
||||
break;
|
||||
case PIO_C:
|
||||
c.append('C');
|
||||
break;
|
||||
case PIO_D:
|
||||
c.append('D');
|
||||
break;
|
||||
case PIO_E:
|
||||
c.append('E');
|
||||
break;
|
||||
case PIO_F:
|
||||
c.append('F');
|
||||
break;
|
||||
case PIO_G:
|
||||
c.append('G');
|
||||
break;
|
||||
case PIO_H:
|
||||
c.append('H');
|
||||
break;
|
||||
}
|
||||
QByteArray state = getValue(address, c);
|
||||
qDebug(dcOneWire()) << "Switch state" << state.toInt();
|
||||
return state.toInt();
|
||||
}
|
||||
|
||||
void OneWire::setSwitchOutput(const QByteArray &address, SwitchChannel channel, bool state)
|
||||
{
|
||||
QByteArray c;
|
||||
c.append("PIO.");
|
||||
switch (channel) {
|
||||
case PIO_A:
|
||||
c.append('A');
|
||||
break;
|
||||
case PIO_B:
|
||||
c.append('B');
|
||||
break;
|
||||
case PIO_C:
|
||||
c.append('C');
|
||||
break;
|
||||
case PIO_D:
|
||||
c.append('D');
|
||||
break;
|
||||
case PIO_E:
|
||||
c.append('E');
|
||||
break;
|
||||
case PIO_F:
|
||||
c.append('F');
|
||||
break;
|
||||
case PIO_G:
|
||||
c.append('G');
|
||||
break;
|
||||
case PIO_H:
|
||||
c.append('H');
|
||||
break;
|
||||
}
|
||||
setValue(address, c, QVariant(state).toByteArray());
|
||||
}
|
||||
|
||||
|
||||
85
onewire/onewire.h
Normal file
85
onewire/onewire.h
Normal file
@ -0,0 +1,85 @@
|
||||
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
||||
* *
|
||||
* Copyright (C) 2018 Bernhard Trinnes <bernhard.trinnes@guh.io> *
|
||||
* *
|
||||
* This file is part of nymea. *
|
||||
* *
|
||||
* This library is free software; you can redistribute it and/or *
|
||||
* modify it under the terms of the GNU Lesser General Public *
|
||||
* License as published by the Free Software Foundation; either *
|
||||
* version 2.1 of the License, or (at your option) any later version. *
|
||||
* *
|
||||
* This library is distributed in the hope that it will be useful, *
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU *
|
||||
* Lesser General Public License for more details. *
|
||||
* *
|
||||
* You should have received a copy of the GNU Lesser General Public *
|
||||
* License along with this library; If not, see *
|
||||
* <http://www.gnu.org/licenses/>. *
|
||||
* *
|
||||
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
||||
|
||||
#ifndef ONEWIRE_H
|
||||
#define ONEWIRE_H
|
||||
|
||||
#include "owcapi.h"
|
||||
|
||||
#include <QObject>
|
||||
|
||||
class OneWire : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
public:
|
||||
enum OneWireProperty {
|
||||
Address, //The entire 64-bit unique ID
|
||||
Crc, //The 8-bit error correction
|
||||
Family, //The 8-bit family code
|
||||
Id, //The 48-bit middle portion of the unique ID number.
|
||||
Locator, //Uses an extension of the 1-wire design from iButtonLink company that associated 1-wire physical connections with a unique 1-wire code.
|
||||
Type //Part name assigned by Dallas Semi. E.g. DS2401
|
||||
};
|
||||
|
||||
enum SwitchChannel {
|
||||
PIO_A,
|
||||
PIO_B,
|
||||
PIO_C,
|
||||
PIO_D,
|
||||
PIO_E,
|
||||
PIO_F,
|
||||
PIO_G,
|
||||
PIO_H
|
||||
};
|
||||
|
||||
struct OneWireDevice {
|
||||
QByteArray address;
|
||||
int family;
|
||||
QByteArray id;
|
||||
QByteArray type;
|
||||
};
|
||||
|
||||
explicit OneWire(QObject *parent = nullptr);
|
||||
~OneWire();
|
||||
bool init(const QByteArray &owfsInitArguments);
|
||||
|
||||
QByteArray getPath();
|
||||
bool discoverDevices();
|
||||
bool interfaceIsAvailable();
|
||||
bool isConnected(const QByteArray &address);
|
||||
|
||||
double getTemperature(const QByteArray &address);
|
||||
QByteArray getType(const QByteArray &address);
|
||||
bool getSwitchOutput(const QByteArray &address, SwitchChannel channel);
|
||||
void setSwitchOutput(const QByteArray &address, SwitchChannel channel, bool state);
|
||||
bool getSwitchInput(const QByteArray &address, SwitchChannel channel);
|
||||
|
||||
private:
|
||||
QByteArray m_path;
|
||||
QByteArray getValue(const QByteArray &address, const QByteArray &deviceType);
|
||||
void setValue(const QByteArray &address, const QByteArray &deviceType, const QByteArray &value);
|
||||
|
||||
signals:
|
||||
void devicesDiscovered(QList<OneWireDevice> devices);
|
||||
};
|
||||
|
||||
#endif // ONEWIRE_H
|
||||
17
onewire/onewire.pro
Normal file
17
onewire/onewire.pro
Normal file
@ -0,0 +1,17 @@
|
||||
include(../plugins.pri)
|
||||
|
||||
TARGET = $$qtLibraryTarget(nymea_devicepluginonewire)
|
||||
|
||||
LIBS += \
|
||||
-low \
|
||||
-lowcapi \
|
||||
|
||||
SOURCES += \
|
||||
devicepluginonewire.cpp \
|
||||
onewire.cpp \
|
||||
|
||||
HEADERS += \
|
||||
devicepluginonewire.h \
|
||||
onewire.h \
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user