cyanobyte
cyanobyte copied to clipboard
Pigweed template
Start work on a template that will create extensions of RegisterDevice for use w/ I2C peripherals.
See RegisterDevice API and Getting Started
- Use
.ccover.cpp WriteRegister8cmd has no semicolon- Add
#include "BMP180.h"at top - Address, Initiator ->
pw::i2c::... - Result ->
pw::Resultand Status ->pw::Status - docs.rst file
- BUILD.gn generation
BUILD.gn (see also sample)
# ...
import("//build_overrides/pigweed.gni")
import("$dir_pw_build/target_types.gni")
import("$dir_pw_chrono/backend.gni")
import("$dir_pw_docgen/docs.gni")
import("$dir_pw_unit_test/test.gni")
pw_source_set("bmp180") {
public = [ "BMP180.h" ]
sources = [ "BMP180.cc" ]
deps = [
"$dir_pw_bytes",
"$dir_pw_chrono:system_clock",
"$dir_pw_i2c:address",
"$dir_pw_i2c:device",
"$dir_pw_i2c:initiator",
"$dir_pw_result",
"$dir_pw_status",
]
}
pw_test_group("tests") {
tests = [
":bmp180_test",
]
}
pw_test("bmp180_test") {
sources = [ "bmp180_test.cc" ]
deps = [ ":bmp180" ]
}
pw_doc_group("docs") {
sources = [ "docs.rst" ]
}
BMP180_test.cc
// Copyright 2021 The Pigweed Authors
//
// Licensed under the Apache License, Version 2.0 (the "License"); you may not
// use this file except in compliance with the License. You may obtain a copy of
// the License at
//
// https://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
// WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
// License for the specific language governing permissions and limitations under
// the License.
#include <array>
#include <chrono>
#include <span>
#include "gtest/gtest.h"
// #include "pw_bytes/array.h"
// #include "pw_bytes/span.h"
// #include "pw_i2c/address.h"
using namespace std::literals::chrono_literals;
namespace pw::i2c {
namespace {
TEST(Transaction, Read) {
EXPECT_EQ(1, 1);
}
} // namespace
} // namespace pw::i2c
BMP180.cc
/*
* Copyright (C) 2020 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* Auto-generated file for BMP180 v0.1.0.
* Generated from peripherals/BMP180.yaml using Cyanobyte Codegen v0.0.2
* Class for BMP180
* Bosch Digital Temperature / Pressure Sensor
*/
#include "BMP180.h"
#define DEVICE_ADDRESS 119
#define REGISTER_CONTROL 244
#define REGISTER_PRESSURECALAC1 170
#define REGISTER_PRESSURECALAC2 172
#define REGISTER_PRESSURECALVB1 182
#define REGISTER_PRESSURECALVB2 184
#define REGISTER_RESULT 246
#define REGISTER_TEMPCAL3 174
#define REGISTER_TEMPCAL4 176
#define REGISTER_TEMPCAL5 178
#define REGISTER_TEMPCAL6 180
#define REGISTER_TEMPCALMC 188
#define REGISTER_TEMPCALMD 190
BMP180::BMP180(pw::i2c::Initiator& initiator):
RegisterDevice(initiator, pw::i2c::Address(119),
std::endian::big,
pw::i2c::RegisterAddressSize::k1Byte) {}
pw::Status BMP180::writeControl(uint8_t data) {
// Hard-coded timeout of 1s.
return WriteRegister8(REGISTER_CONTROL, data, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readPressureCalAC1() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_PRESSURECALAC1, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readPressureCalAC2() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_PRESSURECALAC2, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readPressureCalVB1() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_PRESSURECALVB1, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readPressureCalVB2() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_PRESSURECALVB2, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readResult() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_RESULT, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readTempCal3() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_TEMPCAL3, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readTempCal4() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_TEMPCAL4, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readTempCal5() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_TEMPCAL5, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readTempCal6() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_TEMPCAL6, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readTempCalMC() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_TEMPCALMC, std::chrono::seconds(1));
}
pw::Result<uint16_t> BMP180::readTempCalMD() {
// Hard-coded timeout of 1s.
return ReadRegister16(REGISTER_TEMPCALMD, std::chrono::seconds(1));
}
float BMP180::pressureasMbars() {
short ac1; // Variable declaration
short ac2; // Variable declaration
short ac3; // Variable declaration
uint16_t ac4; // Variable declaration
float b1; // Variable declaration
float c3; // Variable declaration
float c4; // Variable declaration
float p0; // Variable declaration
float p1; // Variable declaration
float p2; // Variable declaration
float pressure; // Variable declaration
float rawComp; // Variable declaration
float temperature; // Variable declaration
short vb1; // Variable declaration
short vb2; // Variable declaration
float x; // Variable declaration
float x1; // Variable declaration
float x2; // Variable declaration
float y; // Variable declaration
float y0; // Variable declaration
float y1; // Variable declaration
float y2; // Variable declaration
float z; // Variable declaration
writeControl(52);
pressure = readResult().value();
temperature = temperatureasCelsius();
pw::chrono::SystemClock::time_point before = pw::chrono::SystemClock::now();
while (pw::chrono::SystemClock::now() - before < std::chrono::milliseconds(10)) {}
rawComp = (temperature-25);
ac1 = readPressureCalAC1().value();
ac2 = readPressureCalAC2().value();
x1 = (160*pow(2, -13)*ac2);
vb2 = readPressureCalVB2().value();
x2 = (pow(160, 2)*pow(2, -25)*vb2);
x = ((x2*pow(rawComp, 2))+(x1*rawComp)+ac1);
ac3 = readTempCal3().value();
c3 = (160*pow(2, -15)*ac3);
ac4 = readTempCal4().value();
c4 = (pow(10, -3)*pow(2, -15)*ac4);
vb1 = readPressureCalVB1().value();
b1 = (pow(160, 2)*pow(2, -30)*vb1);
y0 = (c4*pow(2, 15));
y1 = (c4*c3);
y2 = (c4*b1);
y = ((y2*pow(rawComp, 2))+(y1*rawComp)+y0);
z = ((pressure-x)/y);
p0 = ((3791-8)/1600);
p1 = (1-(7357*pow(2, -30)));
p2 = (3038*100*pow(2, -36));
pressure = ((p2*pow(z, 2))+(p1*z)+p0);
return pressure;
}
float BMP180::temperatureasCelsius() {
short rawComp; // Variable declaration
short rawMc; // Variable declaration
short rawMd; // Variable declaration
float temperature; // Variable declaration
uint16_t varAc5; // Variable declaration
uint16_t varAc6; // Variable declaration
float varC5; // Variable declaration
float varMc; // Variable declaration
float varMd; // Variable declaration
writeControl(46);
temperature = readResult().value();
varAc5 = readTempCal5().value();
varAc6 = readTempCal6().value();
varC5 = ((pow(2, -15)/160)*varAc5);
rawComp = (varC5*(temperature-varAc6));
rawMc = readTempCalMC().value();
varMc = ((pow(2, 11)/pow(160, 2))*rawMc);
rawMd = readTempCalMD().value();
varMd = (rawMd/160);
temperature = (rawComp+(varMc/(rawComp+varMd)));
return temperature;
}
BMP180.h
/*
* Copyright (C) 2020 Google Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*
* Auto-generated file for BMP180 v0.1.0.
* Generated from peripherals/BMP180.yaml using Cyanobyte Codegen v0.0.2
* Class for BMP180
* Bosch Digital Temperature / Pressure Sensor
*/
#pragma once
#include <cmath>
#include "pw_bytes/byte_builder.h"
#include "pw_chrono/system_clock.h"
#include "pw_i2c/address.h"
#include "pw_i2c/device.h"
#include "pw_i2c/register_device.h"
#include "pw_i2c/initiator.h"
#include "pw_result/result.h"
#include "pw_status/status.h"
class BMP180 : pw::i2c::RegisterDevice {
public:
BMP180(pw::i2c::Initiator& initiator);
/**
* Stores the current measurement type.
*/
pw::Status writeControl(uint8_t data);
/**
* Constant register for pressure measurement calibration.
*/
pw::Result<uint16_t> readPressureCalAC1();
/**
* Constant register for pressure measurement calibration.
*/
pw::Result<uint16_t> readPressureCalAC2();
/**
* Constant register for pressure measurement calibration.
*/
pw::Result<uint16_t> readPressureCalVB1();
/**
* Constant register for pressure measurement calibration.
*/
pw::Result<uint16_t> readPressureCalVB2();
/**
* Stores the most recent measurement result.
*/
pw::Result<uint16_t> readResult();
/**
* Third constant register for temperature measurement calibration.
*/
pw::Result<uint16_t> readTempCal3();
/**
* Fourth constant register for temperature measurement calibration.
*/
pw::Result<uint16_t> readTempCal4();
/**
* Fifth constant register for temperature measurement calibration.
*/
pw::Result<uint16_t> readTempCal5();
/**
* Sixth constant register for temperature measurement calibration.
*/
pw::Result<uint16_t> readTempCal6();
/**
* Constant register for temperature measurement calibration.
*/
pw::Result<uint16_t> readTempCalMC();
/**
* Constant register for temperature measurement calibration.
*/
pw::Result<uint16_t> readTempCalMD();
/**
* Reads the pressure in absolute millibars,
* not compensated for sea level.
*/
float pressureasMbars();
/**
* Reads the temperature as a raw value or in Celsius.
*/
float temperatureasCelsius();
};
This all builds, technically. But it gives an error at the very end, maybe because it's building on the host and not for a specific device.
20210604 18:09:31 ERR
20210604 18:09:31 ERR Build error for //pw_chrono:system_clock.NO_BACKEND_SET(//targets/stm32f429i_disc1:stm32f429i_disc1_debug):
20210604 18:09:31 ERR
20210604 18:09:31 ERR Attempted to build the //pw_chrono:system_clock facade with no backend.
20210604 18:09:31 ERR
20210604 18:09:31 ERR If you are using this facade, ensure you have configured a backend
20210604 18:09:31 ERR properly. The build arg for the facade must be set to a valid
20210604 18:09:31 ERR backend in the toolchain. For example, you may need to add a line
20210604 18:09:31 ERR like the following to the toolchain's .gni file:
20210604 18:09:31 ERR
20210604 18:09:31 ERR pw_chrono_<FACADE_NAME>_BACKEND = "//path/to/the:backend"
20210604 18:09:31 ERR
20210604 18:09:31 ERR If you are NOT using this facade, this error may have been triggered
20210604 18:09:31 ERR by trying to build all targets.
20210604 18:09:31 ERR
20210604 18:09:32 ERR Dependency path to this target:
20210604 18:09:32 ERR
20210604 18:09:32 ERR gn path out //:default "//pw_chrono:system_clock.NO_BACKEND_SET(//targets/stm32f429i_disc1:stm32f429i_disc1_debug)"