#define ADC1_DR_ADDRESS ((uint32_t)0x4001244C)
uint16_t ADC1ConvertedValue[4];
void CH12_Config(void)
{
ADC_InitTypeDef ADC_InitStructure;
ADC_CommonInitTypeDef ADC_CommonInitStructure;
DMA_InitTypeDef DMA_InitStructure;
GPIO_InitTypeDef GPIO_InitStructure;
/* Enable ADC1, DMA1 and GPIO clocks ****************************************/
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA2 | RCC_AHB1Periph_GPIOA | RCC_AHB1Periph_GPIOB, ENABLE);
GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AIN;
GPIO_InitStructure.GPIO_Pin = GPIO_Pin_0 |GPIO_Pin_1 | GPIO_Pin_2 |GPIO_Pin_3 | GPIO_Pin_4 |GPIO_Pin_5 | GPIO_Pin_6 |GPIO_Pin_7 ;
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC1, ENABLE);
/* DMA2 Stream0 channel0 configuration **************************************/
DMA_InitStructure.DMA_Channel = DMA_Channel_0;
DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)ADC1_DR_ADDRESS;
DMA_InitStructure.DMA_Memory0BaseAddr = (uint32_t)ADC1ConvertedValue;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralToMemory;
DMA_InitStructure.DMA_BufferSize = 4;
DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord;
DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;
DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;
DMA_InitStructure.DMA_Priority = DMA_Priority_High;
DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;
DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_HalfFull;
DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_Single;
DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_Single;
DMA_Init(DMA2_Stream0, &DMA_InitStructure);
DMA_Cmd(DMA2_Stream0, ENABLE);
/* ADC Common Init **********************************************************/
ADC_CommonInitStructure.ADC_Mode = ADC_Mode_Independent;
ADC_CommonInitStructure.ADC_Prescaler = ADC_Prescaler_Div2;
ADC_CommonInitStructure.ADC_DMAAccessMode = ADC_DMAAccessMode_Disabled;
ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_5Cycles;
ADC_CommonInit(&ADC_CommonInitStructure);
/* ADC1 Init ****************************************************************/
ADC_InitStructure.ADC_Resolution = ADC_Resolution_12b;
ADC_InitStructure.ADC_ScanConvMode = ENABLE;
ADC_InitStructure.ADC_ContinuousConvMode = ENABLE;
ADC_InitStructure.ADC_ExternalTrigConvEdge = ADC_ExternalTrigConvEdge_None;
ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;
ADC_InitStructure.ADC_NbrOfConversion = 4;
ADC_Init(ADC1, &ADC_InitStructure);
/* ADC regular channel2 configuration *************************************/
ADC_RegularChannelConfig(ADC1, ADC_Channel_1, 1, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC1, ADC_Channel_2, 2, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC1, ADC_Channel_5, 3, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC1, ADC_Channel_8, 4, ADC_SampleTime_3Cycles);
/* Enable DMA request after last transfer (Single-ADC mode) */
ADC_DMARequestAfterLastTransferCmd(ADC1, ENABLE);
/* Enable ADC1 DMA */
ADC_DMACmd(ADC1, ENABLE);
/* Enable ADC1 */
ADC_Cmd(ADC1, ENABLE);
}
int main(void)
{
CH12_Config();
ADC_DMACmd(ADC1,ENABLE);
ADC_SoftwareStartConv(ADC1);
while(1)
{
LCD_Write_integer(200,150,ADC1ConvertedValue[0],Green,Black);
LCD_Write_integer(200,165,ADC1ConvertedValue[1],Green,Black);
LCD_Write_integer(200,180,ADC1ConvertedValue[2],Green,Black);
LCD_Write_integer(200,195,ADC1ConvertedValue[3],Green,Black);
}
}
Hata nerede acaba?Veya çok kanal adc okumayı başarabilen varmı?
https://www.picproje.org/index.php/topic,43472.0.html (https://www.picproje.org/index.php/topic,43472.0.html)
DMA tanımlarını F4'e uyarladığında muhtemelen çalışır.
https://www.picproje.org/index.php/topic,41738.0.html (https://www.picproje.org/index.php/topic,41738.0.html)
Bu da DMA ve ST_LIB kullanmadan Interrupt kullanılarak yapılmış bir örnek. Şahsen DMA kullanmadan yapılmasını önermiyorum.
Cortex M4 üzerinde çalışıyorum.Örneğinizi inceledim.Örnekteki kodlar M4'de hata veriyor.Şuan kodları düzenledim çalışıyor fakat 2-3-4 kanaldan okuduğum adc değerleri ufakda olsa birbirinden etkileniyorlar buna çare bulamıyorum
ADC girişlerine nasıl voltaj uyguluyorsun?
ADC kanalını 100 uF kapasitör'le birlikte gnd'ye bağlıyorum.O şekilde uyguluyorum.Direk uyguluyorum sonuç aynı.Örneklerde ADC1 DMA kanal 0 kullanılmış.Ben ADC3 DMA kanal 2 kullandım.Etkileyebilirmi?
//Defines
#define ADC1_DR_ADDRESS ((uint32_t)0x4001244C)
#define ADC3_DR_ADDRESS ((uint32_t)0x4001224C)
//
//Variables
__IO uint16_t ADC3ConvertedValue[10] = 0;
//Variables
void ADC_Initialize(void)
{
ADC_InitTypeDef ADC_InitStructure;
ADC_CommonInitTypeDef ADC_CommonInitStructure;
DMA_InitTypeDef DMA_InitStructure;
GPIO_InitTypeDef GPIO_InitStructure;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_DMA2, ENABLE);
RCC_APB2PeriphClockCmd(RCC_APB2Periph_ADC3, ENABLE);
DMA_InitStructure.DMA_Channel = DMA_Channel_2;
DMA_InitStructure.DMA_PeripheralBaseAddr = (uint32_t)ADC3_DR_ADDRESS;
DMA_InitStructure.DMA_Memory0BaseAddr = (uint32_t)&ADC3ConvertedValue;
DMA_InitStructure.DMA_DIR = DMA_DIR_PeripheralToMemory;
DMA_InitStructure.DMA_BufferSize = 10;
DMA_InitStructure.DMA_PeripheralInc = DMA_PeripheralInc_Disable;
DMA_InitStructure.DMA_MemoryInc = DMA_MemoryInc_Enable;
DMA_InitStructure.DMA_PeripheralDataSize = DMA_PeripheralDataSize_HalfWord;
DMA_InitStructure.DMA_MemoryDataSize = DMA_MemoryDataSize_HalfWord;
DMA_InitStructure.DMA_Mode = DMA_Mode_Circular;
DMA_InitStructure.DMA_Priority = DMA_Priority_High;
DMA_InitStructure.DMA_FIFOMode = DMA_FIFOMode_Disable;
DMA_InitStructure.DMA_FIFOThreshold = DMA_FIFOThreshold_HalfFull;
DMA_InitStructure.DMA_MemoryBurst = DMA_MemoryBurst_Single;
DMA_InitStructure.DMA_PeripheralBurst = DMA_PeripheralBurst_Single;
DMA_Init(DMA2_Stream0, &DMA_InitStructure);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE);
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_0 | GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_AN;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOC, &GPIO_InitStructure);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOB, ENABLE);
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_0 | GPIO_Pin_1;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_AN;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOB, &GPIO_InitStructure);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA, ENABLE);
GPIO_InitStructure.GPIO_Pin=GPIO_Pin_1 | GPIO_Pin_2 | GPIO_Pin_3 | GPIO_Pin_4 | GPIO_Pin_5;
GPIO_InitStructure.GPIO_Mode=GPIO_Mode_AN;
GPIO_InitStructure.GPIO_PuPd=GPIO_PuPd_NOPULL;
GPIO_Init(GPIOA, &GPIO_InitStructure);
ADC_CommonInitStructure.ADC_Mode = ADC_Mode_Independent;
ADC_CommonInitStructure.ADC_Prescaler = ADC_Prescaler_Div2;
ADC_CommonInitStructure.ADC_DMAAccessMode = ADC_DMAAccessMode_Disabled;
ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_5Cycles;
ADC_CommonInit(&ADC_CommonInitStructure);
ADC_InitStructure.ADC_Resolution = ADC_Resolution_8b;
ADC_InitStructure.ADC_ScanConvMode = ENABLE;
ADC_InitStructure.ADC_ContinuousConvMode = ENABLE;
ADC_InitStructure.ADC_ExternalTrigConvEdge = ADC_ExternalTrigConvEdge_None;
ADC_InitStructure.ADC_DataAlign = ADC_DataAlign_Right;
ADC_InitStructure.ADC_NbrOfConversion = 10;
ADC_Init(ADC3, &ADC_InitStructure);
ADC_RegularChannelConfig(ADC3, ADC_Channel_1, 1, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_2, 2, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_3, 3, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_4, 4, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_5, 5, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_8, 6, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_9, 7, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_10, 8, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_11, 9, ADC_SampleTime_3Cycles);
ADC_RegularChannelConfig(ADC3, ADC_Channel_12, 10, ADC_SampleTime_3Cycles);
}
uint16_t ADC_Read(GPIO_TypeDef* GPIOx,uint16_t GPIO_Pin_X)
{
uint16_t ADC_channel;
if(GPIOx==GPIOA & GPIO_Pin_X==GPIO_Pin_1)ADC_channel=ADC3ConvertedValue[0];
if(GPIOx==GPIOA & GPIO_Pin_X==GPIO_Pin_2)ADC_channel=ADC3ConvertedValue[1];
if(GPIOx==GPIOA & GPIO_Pin_X==GPIO_Pin_3)ADC_channel=ADC3ConvertedValue[2];
if(GPIOx==GPIOA & GPIO_Pin_X==GPIO_Pin_4)ADC_channel=ADC3ConvertedValue[3];
if(GPIOx==GPIOA & GPIO_Pin_X==GPIO_Pin_5)ADC_channel=ADC3ConvertedValue[4];
if(GPIOx==GPIOB & GPIO_Pin_X==GPIO_Pin_0)ADC_channel=ADC3ConvertedValue[5];
if(GPIOx==GPIOB & GPIO_Pin_X==GPIO_Pin_1)ADC_channel=ADC3ConvertedValue[6];
if(GPIOx==GPIOC & GPIO_Pin_X==GPIO_Pin_0)ADC_channel=ADC3ConvertedValue[7];
if(GPIOx==GPIOC & GPIO_Pin_X==GPIO_Pin_1)ADC_channel=ADC3ConvertedValue[8];
if(GPIOx==GPIOC & GPIO_Pin_X==GPIO_Pin_2)ADC_channel=ADC3ConvertedValue[9];
return ADC_channel;
}
void ADC_Start(void)
{
ADC_DMARequestAfterLastTransferCmd(ADC3, ENABLE);
ADC_DMACmd(ADC3, ENABLE);
ADC_Cmd(ADC3, ENABLE);
DMA_Cmd(DMA2_Stream0, ENABLE);
ADC_SoftwareStartConv(ADC3);
}
void ADC_Stop(void)
{
ADC_DMARequestAfterLastTransferCmd(ADC3,DISABLE);
ADC_DMACmd(ADC3,DISABLE);
ADC_Cmd(ADC3,DISABLE);
DMA_Cmd(DMA2_Stream0,DISABLE);
}
Yüz Ohmluk 1 kaç tane trimpotu 3.3v a bağla.
Trimpotların orta uçlarından ADC girişlerine gir.
Kanallar biribirinden etkileniyormu diye yazılımını bir daha dene.
Hocam kastettiğim o zaten.Önerin için teşekkür ederimde Elektronik Mühendisiyim, böyle bir hataya düşmem:).Malesef çok fazla oynak değerler geliyor ve 2 kanaldan birini 0'a çektiğimde diğer kanal 1'de bile olsa 4095'den 4070'lere düşüyor.Kanalların birbiriyle ne gibi bi bağlantısı olabilir anlayamıyorum
http://www.cncdesigner.com/wordpress/?p=655 (http://www.cncdesigner.com/wordpress/?p=655)
Örnek alma süresini (Cycle_Time) değerini biraz uzatır mısın?
ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_5Cycles; olan satırı ADC_CommonInitStructure.ADC_TwoSamplingDelay = ADC_TwoSamplingDelay_20Cycles; haline getirdim.Fakat hala pinler birbirinden etkileniyor.
Örnek vermek gerekirse; PC1 ve PC0 pinleri boştayken(parazit durumu) PC1 pinini gnd'ye çektiğimde PC0'dan okunan adc değeri değişmiyor fakat PC0 pinini gnd'ye çektiğimde parazit durumunda 10 bitte 700lerde gösteren PC1 pini 100'lere iniyor.Aynı şekilde PC0'ı 3.3v'ye çektiğimde de 700 lerde olan adc değeri 850 lere çıkıyor.Bunun gibi arasında ilişki bulunan pinler var ve birbirilerinden de etkileniyorlar.Kod olarak da üstte eklediğim kodu kullanmaktayım.Bu soruna bir çare bulursak gerçekten güzel olucak.
Şimdiden Teşekkürler...
Cevap yok mu?
Fırsat bulursam ilgilenmeye çalışacağım.
PC0 pini adc kanallarından birine bağlı bunda sorun yok ancak bord üzerinde dahili olarak usb anahtarlama entegresinin enable pinine de bağlı. R46 direnci ile PC0 üzerindeki adc ölçümleri de doğal olarak etkilenecektir. Bu direnci sıfır ohm olarak kullanmışlar muhtemelen kullanıcı bir jumper ile değiştirme imkanı bulsun demişler...
Ancak PC1 pini doğrudan pin header çıkışına bağlı bu pinden yapılan ölçümlerde sorun olmaması lazım...
[IMG]http://imageshack.us/a/img542/9919/pc0j.jpg[/img]
Alıntı yapılan: alper0017 - 23 Şubat 2013, 14:36:35
Cevap yok mu?
Verdiğim linki okumadınmı? Başından beri olayın giriş empedansı ile ilgili olduğunu belirtmeye çalışıyorum.
ADC girişlerinden sample alma sürelerin kısaldıkça (sample frekansı arttıkça) ADC giriş empedansın küçülür. Uzadıkça büyür. Bu etkinin olumsuz etkisinden ancak çok düşük empedanslı bufferlarla kurtulursun.
ADC dönüşümünün başlangıcındaki sample alma pencere aralığını genişletmek işe yarar fakat asıl önemli olan ADC önündeki devrede.
100 Ohmluk trimpotlarla deneme yaptınmı? Bence yapmadın.
Elimde qrd sensör kartı potanslar herşey var.Ve hepsiyle deneme yaptım.Devre analizinde bir sorun yok.
Olaki elimdeki potansların hepsi yanmış olsun.Sensör kartımda sorunlar olsun.Mikroc ile basit bir kod yazarak tekrar denedim.Mikroc'de herşey sorunsuz çalışırken keil adc3 kodlarımda sorun olduğu apaçık ortada.ADC1'i set etmeye çalışıyorum fakat onda da problem yaşıyorum.Sürekli 0 alıyorum adc kanallarından.Bu işin bi çözümü olmalı ama hiçbiryerde göremiyorum