1
0
Fork 0
mirror of https://github.com/betaflight/betaflight.git synced 2025-07-15 20:35:33 +03:00

sdcard dma config, adc config, bluejayf4 hardware revision

Moved ADC to configuration stored in masterConfig.
 - can remove features for vbat etc in future (perhaps param groups)
 - allows adc to be turned off completely (freeing up dma)

Added feature SDCARD
 - enables it to be turned off.
 - allows for DMA to be turned off (set sdcard_dma=OFF)

Fixed hardware revision to allow BJF4 mini to use the same target (no need for an additional target).
This commit is contained in:
blckmn 2016-11-13 14:25:33 +11:00
parent 7942765ada
commit 17facbea84
19 changed files with 264 additions and 202 deletions

View file

@ -23,9 +23,11 @@
#include "cms/cms.h"
#include "drivers/adc.h"
#include "drivers/pwm_rx.h"
#include "drivers/sound_beeper.h"
#include "drivers/sonar_hcsr04.h"
#include "drivers/sdcard.h"
#include "fc/rc_controls.h"
@ -154,6 +156,10 @@ typedef struct master_s {
pwmConfig_t pwmConfig;
#endif
#ifdef USE_ADC
adcConfig_t adcConfig;
#endif
#ifdef BEEPER
beeperConfig_t beeperConfig;
#endif
@ -178,6 +184,10 @@ typedef struct master_s {
#ifdef OSD
osd_profile_t osdProfile;
#endif
#ifdef USE_SDCARD
sdcardConfig_t sdcardConfig;
#endif
profile_t profile[MAX_PROFILE_COUNT];
uint8_t current_profile_index;
@ -209,8 +219,8 @@ typedef struct master_s {
uint8_t magic_ef; // magic number, should be 0xEF
uint8_t chk; // XOR checksum
/*
do not add properties after the CHK
as it is assumed to exist at length-1
do not add properties after the MAGIC_EF and CHK
as it is assumed to exist at length-2 and length-1
*/
} master_t;

View file

@ -27,19 +27,19 @@
static uint32_t activeFeaturesLatch = 0;
void intFeatureSet(uint32_t mask, master_t *config)
void intFeatureSet(uint32_t mask, uint32_t *features)
{
config->enabledFeatures |= mask;
*features |= mask;
}
void intFeatureClear(uint32_t mask, master_t *config)
void intFeatureClear(uint32_t mask, uint32_t *features)
{
config->enabledFeatures &= ~(mask);
*features &= ~(mask);
}
void intFeatureClearAll(master_t *config)
void intFeatureClearAll(uint32_t *features)
{
config->enabledFeatures = 0;
*features = 0;
}
void latchActiveFeatures()
@ -59,17 +59,17 @@ bool feature(uint32_t mask)
void featureSet(uint32_t mask)
{
intFeatureSet(mask, &masterConfig);
intFeatureSet(mask, &masterConfig.enabledFeatures);
}
void featureClear(uint32_t mask)
{
intFeatureClear(mask, &masterConfig);
intFeatureClear(mask, &masterConfig.enabledFeatures);
}
void featureClearAll()
{
intFeatureClearAll(&masterConfig);
intFeatureClearAll(&masterConfig.enabledFeatures);
}
uint32_t featureMask(void)

View file

@ -24,3 +24,7 @@ void featureSet(uint32_t mask);
void featureClear(uint32_t mask);
void featureClearAll(void);
uint32_t featureMask(void);
void intFeatureClearAll(uint32_t *features);
void intFeatureSet(uint32_t mask, uint32_t *features);
void intFeatureClear(uint32_t mask, uint32_t *features);

View file

@ -33,7 +33,7 @@
//#define DEBUG_ADC_CHANNELS
#ifdef USE_ADC
adc_config_t adcConfig[ADC_CHANNEL_COUNT];
adcOperatingConfig_t adcOperatingConfig[ADC_CHANNEL_COUNT];
volatile uint16_t adcValues[ADC_CHANNEL_COUNT];
uint8_t adcChannelByTag(ioTag_t ioTag)
@ -61,7 +61,7 @@ uint16_t adcGetChannel(uint8_t channel)
debug[3] = adcValues[adcConfig[3].dmaIndex];
}
#endif
return adcValues[adcConfig[channel].dmaIndex];
return adcValues[adcOperatingConfig[channel].dmaIndex];
}
#else

View file

@ -35,14 +35,19 @@ typedef struct adc_config_s {
uint8_t dmaIndex; // index into DMA buffer in case of sparse channels
bool enabled;
uint8_t sampleTime;
} adc_config_t;
} adcOperatingConfig_t;
typedef struct drv_adc_config_s {
bool enableVBat;
bool enableRSSI;
bool enableCurrentMeter;
bool enableExternal1;
} drv_adc_config_t;
typedef struct adcChannelConfig_t {
bool enabled;
ioTag_t ioTag;
} adcChannelConfig_t;
void adcInit(drv_adc_config_t *init);
typedef struct adcConfig_s {
adcChannelConfig_t vbat;
adcChannelConfig_t rssi;
adcChannelConfig_t currentMeter;
adcChannelConfig_t external1;
} adcConfig_t;
void adcInit(adcConfig_t *config);
uint16_t adcGetChannel(uint8_t channel);

View file

@ -61,7 +61,7 @@ typedef struct adcDevice_s {
extern const adcDevice_t adcHardware[];
extern const adcTagMap_t adcTagMap[ADC_TAG_MAP_COUNT];
extern adc_config_t adcConfig[ADC_CHANNEL_COUNT];
extern adcOperatingConfig_t adcOperatingConfig[ADC_CHANNEL_COUNT];
extern volatile uint16_t adcValues[ADC_CHANNEL_COUNT];
uint8_t adcChannelByTag(ioTag_t ioTag);

View file

@ -77,7 +77,7 @@ const adcTagMap_t adcTagMap[] = {
// NAZE rev.5 hardware has PA5 (ADC1_IN5) on breakout pad on bottom of board
//
void adcInit(drv_adc_config_t *init)
void adcInit(adcConfig_t *config)
{
#if !defined(VBAT_ADC_PIN) && !defined(EXTERNAL1_ADC_PIN) && !defined(RSSI_ADC_PIN) && !defined(CURRENT_METER_ADC_PIN)
@ -86,31 +86,23 @@ void adcInit(drv_adc_config_t *init)
uint8_t configuredAdcChannels = 0;
memset(&adcConfig, 0, sizeof(adcConfig));
memset(&adcOperatingConfig, 0, sizeof(adcOperatingConfig));
#ifdef VBAT_ADC_PIN
if (init->enableVBat) {
adcConfig[ADC_BATTERY].tag = IO_TAG(VBAT_ADC_PIN);
if (config->vbat.enabled) {
adcOperatingConfig[ADC_BATTERY].tag = config->vbat.ioTag;
}
#endif
#ifdef RSSI_ADC_PIN
if (init->enableRSSI) {
adcConfig[ADC_RSSI].tag = IO_TAG(RSSI_ADC_PIN);
if (config->rssi.enabled) {
adcOperatingConfig[ADC_RSSI].tag = config->rssi.ioTag; //RSSI_ADC_CHANNEL;
}
#endif
#ifdef EXTERNAL1_ADC_PIN
if (init->enableExternal1) {
adcConfig[ADC_EXTERNAL1].tag = IO_TAG(EXTERNAL1_ADC_PIN);
if (config->external1.enabled) {
adcOperatingConfig[ADC_EXTERNAL1].tag = config->external1.ioTag; //EXTERNAL1_ADC_CHANNEL;
}
#endif
#ifdef CURRENT_METER_ADC_PIN
if (init->enableCurrentMeter) {
adcConfig[ADC_CURRENT].tag = IO_TAG(CURRENT_METER_ADC_PIN);
if (config->currentMeter.enabled) {
adcOperatingConfig[ADC_CURRENT].tag = config->currentMeter.ioTag; //CURRENT_METER_ADC_CHANNEL;
}
#endif
ADCDevice device = adcDeviceByInstance(ADC_INSTANCE);
if (device == ADCINVALID)
@ -118,16 +110,22 @@ void adcInit(drv_adc_config_t *init)
const adcDevice_t adc = adcHardware[device];
bool adcActive = false;
for (int i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].tag)
if (!adcOperatingConfig[i].tag)
continue;
IOInit(IOGetByTag(adcConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcConfig[i].tag), IO_CONFIG(GPIO_Mode_AIN, 0));
adcConfig[i].adcChannel = adcChannelByTag(adcConfig[i].tag);
adcConfig[i].dmaIndex = configuredAdcChannels++;
adcConfig[i].sampleTime = ADC_SampleTime_239Cycles5;
adcConfig[i].enabled = true;
adcActive = true;
IOInit(IOGetByTag(adcOperatingConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcOperatingConfig[i].tag), IO_CONFIG(GPIO_Mode_AIN, 0));
adcOperatingConfig[i].adcChannel = adcChannelByTag(adcOperatingConfig[i].tag);
adcOperatingConfig[i].dmaIndex = configuredAdcChannels++;
adcOperatingConfig[i].sampleTime = ADC_SampleTime_239Cycles5;
adcOperatingConfig[i].enabled = true;
}
if (!adcActive) {
return;
}
RCC_ADCCLKConfig(RCC_PCLK2_Div8); // 9MHz from 72MHz APB2 clock(HSE), 8MHz from 64MHz (HSI)
@ -164,10 +162,10 @@ void adcInit(drv_adc_config_t *init)
uint8_t rank = 1;
for (int i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].enabled) {
if (!adcOperatingConfig[i].enabled) {
continue;
}
ADC_RegularChannelConfig(adc.ADCx, adcConfig[i].adcChannel, rank++, adcConfig[i].sampleTime);
ADC_RegularChannelConfig(adc.ADCx, adcOperatingConfig[i].adcChannel, rank++, adcOperatingConfig[i].sampleTime);
}
ADC_DMACmd(adc.ADCx, ENABLE);

View file

@ -100,40 +100,31 @@ ADCDevice adcDeviceByInstance(ADC_TypeDef *instance)
return ADCINVALID;
}
void adcInit(drv_adc_config_t *init)
void adcInit(adcConfig_t *config)
{
UNUSED(init);
ADC_InitTypeDef ADC_InitStructure;
DMA_InitTypeDef DMA_InitStructure;
uint8_t adcChannelCount = 0;
memset(&adcConfig, 0, sizeof(adcConfig));
memset(&adcOperatingConfig, 0, sizeof(adcOperatingConfig));
#ifdef VBAT_ADC_PIN
if (init->enableVBat) {
adcConfig[ADC_BATTERY].tag = IO_TAG(VBAT_ADC_PIN);
if (config->vbat.enabled) {
adcOperatingConfig[ADC_BATTERY].tag = config->vbat.ioTag;
}
#endif
#ifdef RSSI_ADC_PIN
if (init->enableRSSI) {
adcConfig[ADC_RSSI].tag = IO_TAG(RSSI_ADC_PIN);
if (config->rssi.enabled) {
adcOperatingConfig[ADC_RSSI].tag = config->rssi.ioTag; //RSSI_ADC_CHANNEL;
}
#endif
#ifdef CURRENT_METER_ADC_PIN
if (init->enableCurrentMeter) {
adcConfig[ADC_CURRENT].tag = IO_TAG(CURRENT_METER_ADC_PIN);
if (config->external1.enabled) {
adcOperatingConfig[ADC_EXTERNAL1].tag = config->external1.ioTag; //EXTERNAL1_ADC_CHANNEL;
}
#endif
#ifdef EXTERNAL1_ADC_PIN
if (init->enableExternal1) {
adcConfig[ADC_EXTERNAL1].tag = IO_TAG(EXTERNAL1_ADC_PIN);
if (config->currentMeter.enabled) {
adcOperatingConfig[ADC_CURRENT].tag = config->currentMeter.ioTag; //CURRENT_METER_ADC_CHANNEL;
}
#endif
ADCDevice device = adcDeviceByInstance(ADC_INSTANCE);
if (device == ADCINVALID)
return;
@ -143,18 +134,24 @@ void adcInit(drv_adc_config_t *init)
#endif
adcDevice_t adc = adcHardware[device];
bool adcActive = false;
for (int i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].tag)
if (!adcOperatingConfig[i].tag)
continue;
IOInit(IOGetByTag(adcConfig[i].tag), OWNER_ADC_BATT + i,0);
IOConfigGPIO(IOGetByTag(adcConfig[i].tag), IO_CONFIG(GPIO_Mode_AN, 0, GPIO_OType_OD, GPIO_PuPd_NOPULL));
adcConfig[i].adcChannel = adcChannelByTag(adcConfig[i].tag);
adcConfig[i].dmaIndex = adcChannelCount++;
adcConfig[i].sampleTime = ADC_SampleTime_601Cycles5;
adcConfig[i].enabled = true;
adcActive = true;
IOInit(IOGetByTag(adcOperatingConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcOperatingConfig[i].tag), IO_CONFIG(GPIO_Mode_AN, 0, GPIO_OType_OD, GPIO_PuPd_NOPULL));
adcOperatingConfig[i].adcChannel = adcChannelByTag(adcOperatingConfig[i].tag);
adcOperatingConfig[i].dmaIndex = adcChannelCount++;
adcOperatingConfig[i].sampleTime = ADC_SampleTime_601Cycles5;
adcOperatingConfig[i].enabled = true;
}
if (!adcActive) {
return;
}
RCC_ADCCLKConfig(RCC_ADC12PLLCLK_Div256); // 72 MHz divided by 256 = 281.25 kHz
RCC_ClockCmd(adc.rccADC, ENABLE);
@ -213,10 +210,10 @@ void adcInit(drv_adc_config_t *init)
uint8_t rank = 1;
for (int i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].enabled) {
if (!adcOperatingConfig[i].enabled) {
continue;
}
ADC_RegularChannelConfig(adc.ADCx, adcConfig[i].adcChannel, rank++, adcConfig[i].sampleTime);
ADC_RegularChannelConfig(adc.ADCx, adcOperatingConfig[i].adcChannel, rank++, adcOperatingConfig[i].sampleTime);
}
ADC_Cmd(adc.ADCx, ENABLE);

View file

@ -83,7 +83,7 @@ ADCDevice adcDeviceByInstance(ADC_TypeDef *instance)
return ADCINVALID;
}
void adcInit(drv_adc_config_t *init)
void adcInit(adcConfig_t *config)
{
ADC_InitTypeDef ADC_InitStructure;
DMA_InitTypeDef DMA_InitStructure;
@ -91,37 +91,27 @@ void adcInit(drv_adc_config_t *init)
uint8_t i;
uint8_t configuredAdcChannels = 0;
memset(&adcConfig, 0, sizeof(adcConfig));
memset(&adcOperatingConfig, 0, sizeof(adcOperatingConfig));
#if !defined(VBAT_ADC_PIN) && !defined(EXTERNAL1_ADC_PIN) && !defined(RSSI_ADC_PIN) && !defined(CURRENT_METER_ADC_PIN)
UNUSED(init);
#endif
#ifdef VBAT_ADC_PIN
if (init->enableVBat) {
adcConfig[ADC_BATTERY].tag = IO_TAG(VBAT_ADC_PIN); //VBAT_ADC_CHANNEL;
if (config->vbat.enabled) {
adcOperatingConfig[ADC_BATTERY].tag = config->vbat.ioTag;
}
#endif
#ifdef RSSI_ADC_PIN
if (init->enableRSSI) {
adcConfig[ADC_RSSI].tag = IO_TAG(RSSI_ADC_PIN); //RSSI_ADC_CHANNEL;
if (config->rssi.enabled) {
adcOperatingConfig[ADC_RSSI].tag = config->rssi.ioTag; //RSSI_ADC_CHANNEL;
}
#endif
#ifdef EXTERNAL1_ADC_PIN
if (init->enableExternal1) {
adcConfig[ADC_EXTERNAL1].tag = IO_TAG(EXTERNAL1_ADC_PIN); //EXTERNAL1_ADC_CHANNEL;
if (config->external1.enabled) {
adcOperatingConfig[ADC_EXTERNAL1].tag = config->external1.ioTag; //EXTERNAL1_ADC_CHANNEL;
}
#endif
#ifdef CURRENT_METER_ADC_PIN
if (init->enableCurrentMeter) {
adcConfig[ADC_CURRENT].tag = IO_TAG(CURRENT_METER_ADC_PIN); //CURRENT_METER_ADC_CHANNEL;
if (config->currentMeter.enabled) {
adcOperatingConfig[ADC_CURRENT].tag = config->currentMeter.ioTag; //CURRENT_METER_ADC_CHANNEL;
}
#endif
//RCC_ADCCLKConfig(RCC_ADC12PLLCLK_Div256); // 72 MHz divided by 256 = 281.25 kHz
ADCDevice device = adcDeviceByInstance(ADC_INSTANCE);
if (device == ADCINVALID)
@ -129,18 +119,24 @@ void adcInit(drv_adc_config_t *init)
adcDevice_t adc = adcHardware[device];
for (uint8_t i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].tag)
bool adcActive = false;
for (int i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcOperatingConfig[i].tag)
continue;
IOInit(IOGetByTag(adcConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcConfig[i].tag), IO_CONFIG(GPIO_Mode_AN, 0, GPIO_OType_OD, GPIO_PuPd_NOPULL));
adcConfig[i].adcChannel = adcChannelByTag(adcConfig[i].tag);
adcConfig[i].dmaIndex = configuredAdcChannels++;
adcConfig[i].sampleTime = ADC_SampleTime_480Cycles;
adcConfig[i].enabled = true;
adcActive = true;
IOInit(IOGetByTag(adcOperatingConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcOperatingConfig[i].tag), IO_CONFIG(GPIO_Mode_AN, 0, GPIO_OType_OD, GPIO_PuPd_NOPULL));
adcOperatingConfig[i].adcChannel = adcChannelByTag(adcOperatingConfig[i].tag);
adcOperatingConfig[i].dmaIndex = configuredAdcChannels++;
adcOperatingConfig[i].sampleTime = ADC_SampleTime_480Cycles;
adcOperatingConfig[i].enabled = true;
}
if (!adcActive) {
return;
}
RCC_ClockCmd(adc.rccADC, ENABLE);
dmaInit(dmaGetIdentifier(adc.DMAy_Streamx), OWNER_ADC, 0);
@ -186,10 +182,10 @@ void adcInit(drv_adc_config_t *init)
uint8_t rank = 1;
for (i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].enabled) {
if (!adcOperatingConfig[i].enabled) {
continue;
}
ADC_RegularChannelConfig(adc.ADCx, adcConfig[i].adcChannel, rank++, adcConfig[i].sampleTime);
ADC_RegularChannelConfig(adc.ADCx, adcOperatingConfig[i].adcChannel, rank++, adcOperatingConfig[i].sampleTime);
}
ADC_DMARequestAfterLastTransferCmd(adc.ADCx, ENABLE);

View file

@ -83,7 +83,7 @@ ADCDevice adcDeviceByInstance(ADC_TypeDef *instance)
return ADCINVALID;
}
void adcInit(drv_adc_config_t *init)
void adcInit(adcConfig_t *config)
{
DMA_HandleTypeDef DmaHandle;
ADC_HandleTypeDef ADCHandle;
@ -91,35 +91,27 @@ void adcInit(drv_adc_config_t *init)
uint8_t i;
uint8_t configuredAdcChannels = 0;
memset(&adcConfig, 0, sizeof(adcConfig));
memset(&adcOperatingConfig, 0, sizeof(adcOperatingConfig));
#if !defined(VBAT_ADC_PIN) && !defined(EXTERNAL1_ADC_PIN) && !defined(RSSI_ADC_PIN) && !defined(CURRENT_METER_ADC_PIN)
UNUSED(init);
#endif
#ifdef VBAT_ADC_PIN
if (init->enableVBat) {
adcConfig[ADC_BATTERY].tag = IO_TAG(VBAT_ADC_PIN); //VBAT_ADC_CHANNEL;
if (config->vbat.enabled) {
adcOperatingConfig[ADC_BATTERY].tag = config->vbat.ioTag;
}
#endif
#ifdef RSSI_ADC_PIN
if (init->enableRSSI) {
adcConfig[ADC_RSSI].tag = IO_TAG(RSSI_ADC_PIN); //RSSI_ADC_CHANNEL;
if (config->rssi.enabled) {
adcOperatingConfig[ADC_RSSI].tag = config->rssi.ioTag; //RSSI_ADC_CHANNEL;
}
#endif
#ifdef EXTERNAL1_ADC_PIN
if (init->enableExternal1) {
adcConfig[ADC_EXTERNAL1].tag = IO_TAG(EXTERNAL1_ADC_PIN); //EXTERNAL1_ADC_CHANNEL;
if (config->external1.enabled) {
adcOperatingConfig[ADC_EXTERNAL1].tag = config->external1.ioTag; //EXTERNAL1_ADC_CHANNEL;
}
#endif
#ifdef CURRENT_METER_ADC_PIN
if (init->enableCurrentMeter) {
adcConfig[ADC_CURRENT].tag = IO_TAG(CURRENT_METER_ADC_PIN); //CURRENT_METER_ADC_CHANNEL;
if (config->currentMeter.enabled) {
adcOperatingConfig[ADC_CURRENT].tag = config->currentMeter.ioTag; //CURRENT_METER_ADC_CHANNEL;
}
#endif
ADCDevice device = adcDeviceByInstance(ADC_INSTANCE);
if (device == ADCINVALID)
@ -127,18 +119,23 @@ void adcInit(drv_adc_config_t *init)
adcDevice_t adc = adcHardware[device];
for (uint8_t i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].tag)
bool adcActive = false;
for (int i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcOperatingConfig[i].tag)
continue;
IOInit(IOGetByTag(adcConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcConfig[i].tag), IO_CONFIG(GPIO_MODE_ANALOG, 0, GPIO_NOPULL));
adcConfig[i].adcChannel = adcChannelByTag(adcConfig[i].tag);
adcConfig[i].dmaIndex = configuredAdcChannels++;
adcConfig[i].sampleTime = ADC_SAMPLETIME_480CYCLES;
adcConfig[i].enabled = true;
adcActive = true;
IOInit(IOGetByTag(adcOperatingConfig[i].tag), OWNER_ADC_BATT + i, 0);
IOConfigGPIO(IOGetByTag(adcOperatingConfig[i].tag), IO_CONFIG(GPIO_MODE_ANALOG, 0, GPIO_NOPULL));
adcOperatingConfig[i].adcChannel = adcChannelByTag(adcOperatingConfig[i].tag);
adcOperatingConfig[i].dmaIndex = configuredAdcChannels++;
adcOperatingConfig[i].sampleTime = ADC_SAMPLETIME_480CYCLES;
adcOperatingConfig[i].enabled = true;
}
if (!adcActive) {
return;
}
RCC_ClockCmd(adc.rccADC, ENABLE);
dmaInit(dmaGetIdentifier(adc.DMAy_Streamx), OWNER_ADC, 0);
@ -187,13 +184,13 @@ void adcInit(drv_adc_config_t *init)
uint8_t rank = 1;
for (i = 0; i < ADC_CHANNEL_COUNT; i++) {
if (!adcConfig[i].enabled) {
if (!adcOperatingConfig[i].enabled) {
continue;
}
ADC_ChannelConfTypeDef sConfig;
sConfig.Channel = adcConfig[i].adcChannel;
sConfig.Channel = adcOperatingConfig[i].adcChannel;
sConfig.Rank = rank++;
sConfig.SamplingTime = adcConfig[i].sampleTime;
sConfig.SamplingTime = adcOperatingConfig[i].sampleTime;
sConfig.Offset = 0;
/*##-3- Configure ADC regular channel ######################################*/

View file

@ -20,7 +20,11 @@
#include <stdint.h>
#include <stdbool.h>
typedef struct sdcardMetadata_t {
typedef struct sdcardConfig_s {
uint8_t useDma;
} sdcardConfig_t;
typedef struct sdcardMetadata_s {
uint8_t manufacturerID;
uint16_t oemID;

View file

@ -45,6 +45,7 @@
#include "drivers/max7456.h"
#include "drivers/sound_beeper.h"
#include "drivers/light_ws2811strip.h"
#include "drivers/sdcard.h"
#include "fc/config.h"
#include "fc/rc_controls.h"
@ -101,18 +102,12 @@
#define BRUSHLESS_MOTORS_PWM_RATE 400
#endif
master_t masterConfig; // master config struct with data independent from profiles
profile_t *currentProfile;
static uint8_t currentControlRateProfileIndex = 0;
controlRateConfig_t *currentControlRateProfile;
void intFeatureClearAll(master_t *config);
void intFeatureSet(uint32_t mask, master_t *config);
void intFeatureClear(uint32_t mask, master_t *config);
static void resetAccelerometerTrims(flightDynamicsTrims_t *accelerometerTrims)
{
accelerometerTrims->values.pitch = 0;
@ -314,6 +309,44 @@ void resetSonarConfig(sonarConfig_t *sonarConfig)
}
#endif
#ifdef USE_SDCARD
void resetsdcardConfig(sdcardConfig_t *sdcardConfig)
{
#if defined(SDCARD_DMA_CHANNEL_TX)
sdcardConfig->useDma = true;
#else
sdcardConfig->useDma = false;
#endif
}
#endif
#ifdef USE_ADC
void resetAdcConfig(adcConfig_t *adcConfig)
{
#ifdef VBAT_ADC_PIN
adcConfig->vbat.enabled = true;
adcConfig->vbat.ioTag = IO_TAG(VBAT_ADC_PIN);
#endif
#ifdef EXTERNAL1_ADC_PIN
adcConfig->external1.enabled = true;
adcConfig->external1.ioTag = IO_TAG(EXTERNAL1_ADC_PIN);
#endif
#ifdef CURRENT_METER_ADC_PIN
adcConfig->currentMeter.enabled = true;
adcConfig->currentMeter.ioTag = IO_TAG(CURRENT_METER_ADC_PIN);
#endif
#ifdef RSSI_ADC_PIN
adcConfig->rssi.enabled = true;
adcConfig->rssi.ioTag = IO_TAG(RSSI_ADC_PIN);
#endif
}
#endif
#ifdef BEEPER
void resetBeeperConfig(beeperConfig_t *beeperConfig)
{
@ -490,30 +523,32 @@ void createDefaultConfig(master_t *config)
// Clear all configuration
memset(config, 0, sizeof(master_t));
intFeatureClearAll(config);
intFeatureSet(DEFAULT_RX_FEATURE | FEATURE_FAILSAFE , config);
uint32_t *featuresPtr = &config->enabledFeatures;
intFeatureClearAll(featuresPtr);
intFeatureSet(DEFAULT_RX_FEATURE | FEATURE_FAILSAFE , featuresPtr);
#ifdef DEFAULT_FEATURES
intFeatureSet(DEFAULT_FEATURES, config);
intFeatureSet(DEFAULT_FEATURES, featuresPtr);
#endif
#ifdef OSD
intFeatureSet(FEATURE_OSD, config);
intFeatureSet(FEATURE_OSD, featuresPtr);
osdResetConfig(&config->osdProfile);
#endif
#ifdef BOARD_HAS_VOLTAGE_DIVIDER
// only enable the VBAT feature by default if the board has a voltage divider otherwise
// the user may see incorrect readings and unexpected issues with pin mappings may occur.
intFeatureSet(FEATURE_VBAT, config);
intFeatureSet(FEATURE_VBAT, featuresPtr);
#endif
config->version = EEPROM_CONF_VERSION;
config->mixerMode = MIXER_QUADX;
// global settings
config->current_profile_index = 0; // default profile
config->current_profile_index = 0; // default profile
config->dcm_kp = 2500; // 1.0 * 10000
config->dcm_ki = 0; // 0.003 * 10000
config->dcm_ki = 0; // 0.003 * 10000
config->gyro_lpf = 0; // 256HZ default
#ifdef STM32F10X
config->gyro_sync_denom = 8;
@ -562,6 +597,10 @@ void createDefaultConfig(master_t *config)
resetTelemetryConfig(&config->telemetryConfig);
#endif
#ifdef USE_ADC
resetAdcConfig(&config->adcConfig);
#endif
#ifdef BEEPER
resetBeeperConfig(&config->beeperConfig);
#endif
@ -570,6 +609,11 @@ void createDefaultConfig(master_t *config)
resetSonarConfig(&config->sonarConfig);
#endif
#ifdef USE_SDCARD
intFeatureSet(FEATURE_SDCARD, featuresPtr);
resetsdcardConfig(&config->sdcardConfig);
#endif
#ifdef SERIALRX_PROVIDER
config->rxConfig.serialrx_provider = SERIALRX_PROVIDER;
#else
@ -708,10 +752,10 @@ void createDefaultConfig(master_t *config)
#ifdef BLACKBOX
#if defined(ENABLE_BLACKBOX_LOGGING_ON_SPIFLASH_BY_DEFAULT)
intFeatureSet(FEATURE_BLACKBOX, config);
intFeatureSet(FEATURE_BLACKBOX, featuresPtr);
config->blackbox_device = BLACKBOX_DEVICE_FLASH;
#elif defined(ENABLE_BLACKBOX_LOGGING_ON_SDCARD_BY_DEFAULT)
intFeatureSet(FEATURE_BLACKBOX, config);
intFeatureSet(FEATURE_BLACKBOX, featuresPtr);
config->blackbox_device = BLACKBOX_DEVICE_SDCARD;
#else
config->blackbox_device = BLACKBOX_DEVICE_SERIAL;
@ -735,7 +779,6 @@ void createDefaultConfig(master_t *config)
targetConfiguration(config);
#endif
// copy first profile into remaining profile
for (int i = 1; i < MAX_PROFILE_COUNT; i++) {
memcpy(&config->profile[i], &config->profile[0], sizeof(profile_t));
@ -940,6 +983,10 @@ void validateAndFixConfig(void)
if (!isSerialConfigValid(serialConfig)) {
resetSerialConfig(serialConfig);
}
#if defined(TARGET_VALIDATECONFIG)
targetValidateConfiguration(&masterConfig);
#endif
}
void readEEPROMAndNotify(void)

View file

@ -51,7 +51,7 @@ typedef enum {
FEATURE_CHANNEL_FORWARDING = 1 << 20,
FEATURE_TRANSPONDER = 1 << 21,
FEATURE_AIRMODE = 1 << 22,
//FEATURE_SUPEREXPO_RATES = 1 << 23,
FEATURE_SDCARD = 1 << 23,
FEATURE_VTX = 1 << 24,
FEATURE_RX_SPI = 1 << 25,
FEATURE_SOFTSPI = 1 << 26,
@ -86,4 +86,6 @@ bool canSoftwareSerialBeUsed(void);
uint16_t getCurrentMinthrottle(void);
struct master_s;
void targetConfiguration(struct master_s *config);
void targetValidateConfiguration(struct master_s *config);

View file

@ -230,7 +230,7 @@ static const char * const featureNames[] = {
"SONAR", "TELEMETRY", "CURRENT_METER", "3D", "RX_PARALLEL_PWM",
"RX_MSP", "RSSI_ADC", "LED_STRIP", "DISPLAY", "OSD",
"BLACKBOX", "CHANNEL_FORWARDING", "TRANSPONDER", "AIRMODE",
" ", "VTX", "RX_SPI", "SOFTSPI", NULL
"SDCARD", "VTX", "RX_SPI", "SOFTSPI", NULL
};
// sync this with rxFailsafeChannelMode_e
@ -944,7 +944,9 @@ const clivalue_t valueTable[] = {
{ "vtx_channel", VAR_UINT8 | MASTER_VALUE, &masterConfig.vtx_channel, .config.minmax = { 0, 39 } },
{ "vtx_power", VAR_UINT8 | MASTER_VALUE, &masterConfig.vtx_power, .config.minmax = { 0, 1 } },
#endif
#ifdef USE_SDCARD
{ "sdcard_dma", VAR_UINT8 | MASTER_VALUE | MODE_LOOKUP, &masterConfig.sdcardConfig.useDma, .config.lookup = { TABLE_OFF_ON } },
#endif
#ifdef OSD
{ "osd_video_system", VAR_UINT8 | MASTER_VALUE, &masterConfig.osdProfile.video_system, .config.minmax = { 0, 2 } },
{ "osd_row_shiftdown", VAR_UINT8 | MASTER_VALUE, &masterConfig.osdProfile.row_shiftdown, .config.minmax = { 0, 1 } },

View file

@ -373,21 +373,11 @@ void init(void)
#endif
#ifdef USE_ADC
drv_adc_config_t adc_params;
adc_params.enableVBat = feature(FEATURE_VBAT);
adc_params.enableRSSI = feature(FEATURE_RSSI_ADC);
adc_params.enableCurrentMeter = feature(FEATURE_CURRENT_METER);
adc_params.enableExternal1 = false;
#ifdef OLIMEXINO
adc_params.enableExternal1 = true;
#endif
#ifdef NAZE
// optional ADC5 input on rev.5 hardware
adc_params.enableExternal1 = (hardwareRevision >= NAZE32_REV5);
#endif
adcInit(&adc_params);
/* these can be removed from features! */
masterConfig.adcConfig.vbat.enabled = feature(FEATURE_VBAT);
masterConfig.adcConfig.currentMeter.enabled = feature(FEATURE_CURRENT_METER);
masterConfig.adcConfig.rssi.enabled = feature(FEATURE_RSSI_ADC);
adcInit(&masterConfig.adcConfig);
#endif
@ -527,28 +517,11 @@ void init(void)
#endif
#ifdef USE_SDCARD
bool sdcardUseDMA = false;
sdcardInsertionDetectInit();
#ifdef SDCARD_DMA_CHANNEL_TX
#if defined(LED_STRIP) && defined(WS2811_DMA_CHANNEL)
// Ensure the SPI Tx DMA doesn't overlap with the led strip
#if defined(STM32F4) || defined(STM32F7)
sdcardUseDMA = !feature(FEATURE_LED_STRIP) || SDCARD_DMA_CHANNEL_TX != WS2811_DMA_STREAM;
#else
sdcardUseDMA = !feature(FEATURE_LED_STRIP) || SDCARD_DMA_CHANNEL_TX != WS2811_DMA_CHANNEL;
#endif
#else
sdcardUseDMA = true;
#endif
#endif
sdcard_init(sdcardUseDMA);
afatfs_init();
if (feature(FEATURE_SDCARD)) {
sdcardInsertionDetectInit();
sdcard_init(masterConfig.sdcardConfig.useDma);
afatfs_init();
}
#endif
if (masterConfig.gyro_lpf > 0 && masterConfig.gyro_lpf < 7) {

View file

@ -21,6 +21,9 @@
#include <platform.h>
#include "config/config_master.h"
#include "config/feature.h"
#include "blackbox/blackbox_io.h"
#include "hardware_revision.h"
@ -32,4 +35,24 @@ void targetConfiguration(master_t *config)
config->sensorAlignmentConfig.acc_align = CW180_DEG;
config->beeperConfig.ioTag = IO_TAG(BEEPER_OPT);
}
if (hardwareRevision == BJF4_MINI_REV3A || hardwareRevision == BJF4_REV1) {
intFeatureClear(FEATURE_SDCARD, &config->enabledFeatures);
}
if (hardwareRevision == BJF4_MINI_REV3A) {
config->adcConfig.vbat.ioTag = IO_TAG(PA4);
}
}
void targetValidateConfiguration(master_t *config)
{
/* make sure the SDCARD cannot be turned on */
if (hardwareRevision == BJF4_MINI_REV3A || hardwareRevision == BJF4_REV1) {
intFeatureClear(FEATURE_SDCARD, &config->enabledFeatures);
if (config->blackbox_device == BLACKBOX_DEVICE_SDCARD) {
config->blackbox_device = BLACKBOX_DEVICE_FLASH;
}
}
}

View file

@ -45,10 +45,6 @@ void detectHardwareRevision(void)
IOInit(pin1, OWNER_SYSTEM, 1);
IOConfigGPIO(pin1, IOCFG_IPU);
IO_t pin2 = IOGetByTag(IO_TAG(PB13));
IOInit(pin2, OWNER_SYSTEM, 2);
IOConfigGPIO(pin2, IOCFG_IPU);
// Check hardware revision
delayMicroseconds(10); // allow configuration to settle
@ -57,10 +53,17 @@ void detectHardwareRevision(void)
if only PB12 is tied to GND then it is a Rev3 (full size)
*/
if (!IORead(pin1)) {
if (!IORead(pin2)) {
hardwareRevision = BJF4_REV3A;
}
hardwareRevision = BJF4_REV3;
} else {
IO_t pin2 = IOGetByTag(IO_TAG(PB13));
IOInit(pin2, OWNER_SYSTEM, 2);
IOConfigGPIO(pin2, IOCFG_OUT_PP);
IOWrite(pin2, false);
if (!IORead(pin1)) {
hardwareRevision = BJF4_MINI_REV3A;
}
}
if (hardwareRevision == UNKNOWN) {

View file

@ -21,7 +21,7 @@ typedef enum bjf4HardwareRevision_t {
BJF4_REV1, // Flash
BJF4_REV2, // SDCard
BJF4_REV3, // SDCard + Flash
BJF4_REV3A, // Flash (20x20 mini format)
BJF4_MINI_REV3A, // Flash (20x20 mini format)
} bjf4HardwareRevision_e;
extern uint8_t hardwareRevision;

View file

@ -18,6 +18,7 @@
#pragma once
#define TARGET_BOARD_IDENTIFIER "BJF4"
#define TARGET_CONFIG
#define TARGET_VALIDATECONFIG
#define CONFIG_START_FLASH_ADDRESS (0x08080000) //0x08080000 to 0x080A0000 (FLASH_Sector_8)