سلام. من از ADC در نرم افزار BASCOM استفاده می کنم و آن را در مود Single_Ended و unSigned و با ولتاژ رفرنس داخلی 1v راه اندازی کردم.
حالا چندتا سوال برام پیش اومده:
اول اینکه من وقتی از دو ADCa و ADCb فقط ADCa را کانفیگ می کنم، ولی در زمان خواندن مقدار ADC، به کانال 15 مالتیپلکس میکنم، میکرو میاد مقدار ADC7 از پورت B را برای من می خونه. در حالی که من فقط ADCa را کانفیگ کردم. همچنین مالتیپکس به کانال 0، میاد و مقدار روی ADC0 روی پورت A را می خواند. و با مالتیپلکس به کانال 7، میاد و ADC7 از پورت A را می خواند.
دقیقا عکس این قضیه هم صحت داره که : اگر فقط ADCb را کانفیگ می کنم، ولی در زمان خواندن مقدار ADC، به کانال 15 مالتیپلکس میکنم، میکرو میاد مقدار ADC7 از پورت A را برای من می خونه. در حالی که من فقط ADCb را کانفیگ کردم. همچنین مالتیپکس به کانال 0، میاد و مقدار روی ADC0 روی پورت B را می خواند. و با مالتیپلکس به کانال 7، میاد و ADC7 از پورت B را می خواند.
خوب اینجا چه اتفاقی می افته که من به ADC روی دو پورت دسترسی دارم. آخه اگر ADC روی که پورت کانفیگ بشه دیگه نمیشه از اون پورت در حالت I/O استفاده کرد. پس یعنی اگر من ADCa را کانفیگ کنم، پورتB هم به باد رفته؟؟؟
دوم اینکه چه طور میشه با این ADC دقیق کار کرد؟؟ در مود Single_Ended و unSigned می دونید که یک افستی وجود داره به این معنی که اگر پورت را زمین هم کنید، میکرو میاد و یک مقداری که حدودآ برابر 0.05*VReff هست را نشون میده که برای ولتاژ رفرنس 1 ولت می شه حدود 50mv=204. ولی وقتی من پایه ی ADC را زمین می کنم مقدار حدودی 106 را بهم میده که تازه این مقدار حدودآ 10 تا هم بالا پایین میشه (تازه با 20 بار خواندن ADC و معدل گرفتن). تازه این ولتاژ پایدار و تکرار پذیر هم خیلی نیست. لطفا راهنمایی کند که مشکل کار کجاست. در زیر هم یک نمونه کد قرار دادم.
با تشکر
[code=vb]$regfile = "xm128a3udef.dat"
$crystal = 32000000
$hwstack = 100
$swstack = 100
$framesize = 100
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ System OSC & Clock ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'>>>>>> WORKS <<<<<<<
'Try Overclocking for Logic Analyzer Sampling.
'Xmega Max Spec is 32 MHz.
'Incrementally Incr PLL using 2 MHz Int Osc.
'PLL = x16 = 32 MHz = Baseline, in spec.
'Set up the Xmega clock.
'Run on Internal 2 MHz Osc, PLL= x25, Clk = 50 MHz.
'This MANUALLY turns on the Xmega PLL.
'Xmega runs at 2MHz on power up.
Osc_ctrl = 15 'All Osc ON, PLL Off
Clk_psctrl = 0 'No PreScaler in use
Osc_xoscctrl = 195 '12-16MHz, 256 Clks
Osc_pllctrl = 25 'PLL: Int 2 MHz Osc x 25 !!!
Waitms 3
Osc_ctrl = 31 'PLL ON, All Osc Sources On
Waitms 3
Cpu_ccp = 216 'Config Change Protection
Clk_ctrl = 1 '4=Use PLL as Clock Source / 1=32MHz internal
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ System OSC & Clock ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'******************************************** **********************************
'************************ Config Interrupts & Includes ************************
'******************************************** **********************************
Config Submode = New
Config Priority = Static , Vector = Application , Lo = Enabled 'config interrupts
Enable Interrupts
'******************************************** **********************************
'************************ Config Interrupts & Includes ************************
'******************************************** **********************************
Config Com6 = 9600 , Mode = 0 , Parity = None , Stopbits = 1 , Databits = 8
Open "Com6:" For Binary As #1 'Must Open Com1 Before Printing'
Print #1 , "Hello"
Print #1 , "Hello"
Print #1 , "Hello"
Config Adca = Single , Convmode = Unsigned , Resolution = 12bit , Dma = Off _
, Reference = Int1v , Event_mode = None , Prescaler = 32 , , Ch0_gain = 2 _
, Ch0_inp = Single_ended , Mux0 = 0
Sw1 Alias Pinf.3
Sw2 Alias Pinf.4
Config Sw1 = Input
Config Sw2 = Input
Dim Count1 As Integer
Dim W1 As Word , W2 As Word
Dim S1 As Single , A1 As Single
Dim S2 As Single , A2 As Single
Do
If Sw1 = 1 Then
Waitms 30
If Sw1 = 1 Then
Waitms 200
Gosub Sww1
End If
End If
If Sw2 = 1 Then
Waitms 30
If Sw2 = 1 Then
Waitms 200
Gosub Sww2
End If
End If
If Count1 <= 20 Then
W1 = Getadc(adca , 0 , &B0_0000_000) 'Read from ADC0 from PortA
W2 = Getadc(adca , 0 , &B0_1111_000) 'Read from ADC7 from PortB
Incr Count1
S1 = S1 + W1
S2 = S2 + W2
Else
A1 = S1 / Count1
A2 = S2 / Count1
Count1 = 0
S1 = 0
S2 = 0
Print #1 , "A1= " ; A1 ; "A2=" ; A2
Waitms 400
End If
Waitms 1
Loop
Close #1
End
End[/code]
حالا چندتا سوال برام پیش اومده:
اول اینکه من وقتی از دو ADCa و ADCb فقط ADCa را کانفیگ می کنم، ولی در زمان خواندن مقدار ADC، به کانال 15 مالتیپلکس میکنم، میکرو میاد مقدار ADC7 از پورت B را برای من می خونه. در حالی که من فقط ADCa را کانفیگ کردم. همچنین مالتیپکس به کانال 0، میاد و مقدار روی ADC0 روی پورت A را می خواند. و با مالتیپلکس به کانال 7، میاد و ADC7 از پورت A را می خواند.
دقیقا عکس این قضیه هم صحت داره که : اگر فقط ADCb را کانفیگ می کنم، ولی در زمان خواندن مقدار ADC، به کانال 15 مالتیپلکس میکنم، میکرو میاد مقدار ADC7 از پورت A را برای من می خونه. در حالی که من فقط ADCb را کانفیگ کردم. همچنین مالتیپکس به کانال 0، میاد و مقدار روی ADC0 روی پورت B را می خواند. و با مالتیپلکس به کانال 7، میاد و ADC7 از پورت B را می خواند.
خوب اینجا چه اتفاقی می افته که من به ADC روی دو پورت دسترسی دارم. آخه اگر ADC روی که پورت کانفیگ بشه دیگه نمیشه از اون پورت در حالت I/O استفاده کرد. پس یعنی اگر من ADCa را کانفیگ کنم، پورتB هم به باد رفته؟؟؟
دوم اینکه چه طور میشه با این ADC دقیق کار کرد؟؟ در مود Single_Ended و unSigned می دونید که یک افستی وجود داره به این معنی که اگر پورت را زمین هم کنید، میکرو میاد و یک مقداری که حدودآ برابر 0.05*VReff هست را نشون میده که برای ولتاژ رفرنس 1 ولت می شه حدود 50mv=204. ولی وقتی من پایه ی ADC را زمین می کنم مقدار حدودی 106 را بهم میده که تازه این مقدار حدودآ 10 تا هم بالا پایین میشه (تازه با 20 بار خواندن ADC و معدل گرفتن). تازه این ولتاژ پایدار و تکرار پذیر هم خیلی نیست. لطفا راهنمایی کند که مشکل کار کجاست. در زیر هم یک نمونه کد قرار دادم.
با تشکر
[code=vb]$regfile = "xm128a3udef.dat"
$crystal = 32000000
$hwstack = 100
$swstack = 100
$framesize = 100
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ System OSC & Clock ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'>>>>>> WORKS <<<<<<<
'Try Overclocking for Logic Analyzer Sampling.
'Xmega Max Spec is 32 MHz.
'Incrementally Incr PLL using 2 MHz Int Osc.
'PLL = x16 = 32 MHz = Baseline, in spec.
'Set up the Xmega clock.
'Run on Internal 2 MHz Osc, PLL= x25, Clk = 50 MHz.
'This MANUALLY turns on the Xmega PLL.
'Xmega runs at 2MHz on power up.
Osc_ctrl = 15 'All Osc ON, PLL Off
Clk_psctrl = 0 'No PreScaler in use
Osc_xoscctrl = 195 '12-16MHz, 256 Clks
Osc_pllctrl = 25 'PLL: Int 2 MHz Osc x 25 !!!
Waitms 3
Osc_ctrl = 31 'PLL ON, All Osc Sources On
Waitms 3
Cpu_ccp = 216 'Config Change Protection
Clk_ctrl = 1 '4=Use PLL as Clock Source / 1=32MHz internal
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ System OSC & Clock ^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
'******************************************** **********************************
'************************ Config Interrupts & Includes ************************
'******************************************** **********************************
Config Submode = New
Config Priority = Static , Vector = Application , Lo = Enabled 'config interrupts
Enable Interrupts
'******************************************** **********************************
'************************ Config Interrupts & Includes ************************
'******************************************** **********************************
Config Com6 = 9600 , Mode = 0 , Parity = None , Stopbits = 1 , Databits = 8
Open "Com6:" For Binary As #1 'Must Open Com1 Before Printing'
Print #1 , "Hello"
Print #1 , "Hello"
Print #1 , "Hello"
Config Adca = Single , Convmode = Unsigned , Resolution = 12bit , Dma = Off _
, Reference = Int1v , Event_mode = None , Prescaler = 32 , , Ch0_gain = 2 _
, Ch0_inp = Single_ended , Mux0 = 0
Sw1 Alias Pinf.3
Sw2 Alias Pinf.4
Config Sw1 = Input
Config Sw2 = Input
Dim Count1 As Integer
Dim W1 As Word , W2 As Word
Dim S1 As Single , A1 As Single
Dim S2 As Single , A2 As Single
Do
If Sw1 = 1 Then
Waitms 30
If Sw1 = 1 Then
Waitms 200
Gosub Sww1
End If
End If
If Sw2 = 1 Then
Waitms 30
If Sw2 = 1 Then
Waitms 200
Gosub Sww2
End If
End If
If Count1 <= 20 Then
W1 = Getadc(adca , 0 , &B0_0000_000) 'Read from ADC0 from PortA
W2 = Getadc(adca , 0 , &B0_1111_000) 'Read from ADC7 from PortB
Incr Count1
S1 = S1 + W1
S2 = S2 + W2
Else
A1 = S1 / Count1
A2 = S2 / Count1
Count1 = 0
S1 = 0
S2 = 0
Print #1 , "A1= " ; A1 ; "A2=" ; A2
Waitms 400
End If
Waitms 1
Loop
Close #1
End
End[/code]
دیدگاه