ARM, STM32, آموزش, آموزش STM32 با توابع LL, توصیه شده, مقاله های سیسوگ

راه‌اندازی واحد ADC توسط DMA در STM32 | آموزش STM32 با توابع LL

راه‌اندازی واحد ADC توسط DMA

در بخش دهم، با واحد ADC و در بخش قبلی هم با ریدایرکت کردن Printf و Scanf آشنا شدیم. در این بخش، می‌خواهیم نحوه‌ی راه‌اندازی واحد ADC توسط DMA (بورد Blue Pill) را توضیح دهیم و البته به کمک واحد DMA از این واحد اطلاعات را دریافت و در حافظه ذخیره کنیم. واحد DMA یا Direct Memory Access همان‌طور که از نام آن مشخص است برای کنترل ارتباط با حافظه به‌کار می‌رود. مزیت استفاده از DMA این است که این واحد مستقل از پردازنده اصلی می‌تواند ورود و خروج اطلاعات بین وسایل جانبی و حافظه را کنترل کند، درنتیجه توان پردازشی پردازنده می‌تواند صرف انجام کارهای دیگر شود.

 

مرحله اول ایجاد پروژه در محیط STM32CubeMX

برای راه‌اندازی واحد ADC توسط DMA ، مثل قبل تنظیمات کلاک و دیباگ و انتخاب پین‌های ورودی و خروجی موردنیاز انجام می‌شود. در صورت نیاز به ارسال اطلاعات دریافتی از ADC، تنظیم USART نیز باید به همان شکل قبل انجام شود. برای تنظیم ADC در منوی Analog، واحد ADC1 را انتخاب می‌کنیم. در بخش Mode کانال‌های موردنیاز انتخاب می‌شوند (در اینجا کانال 0 و کانال 1 انتخاب‌شده‌اند). در بخش Configuration و از تب پارامترها Continuous Conversion Mode را در حالت Enable قرار می‌دهیم (زیرا می‌خواهیم به‌طور پیوسته مقدار ورودی در کانال‌های ADC را بخوانیم) درصورتی‌که مانند این مثال بیش از یک کانال انتخاب‌شده باشند باید Scan Conversion Mode نیز فعال کنیم. بدین منظور ابتدا Number Of Conversion را روی تعداد موردنظر تنظیم می‌کنیم (در اینجا 2) اولویت تبدیل کانال‌ها و همچنین مدت‌زمان نمونه‌برداری را نیز طبق شکل زیر تنظیم می‌شوند:

 

نکته: تب بعدی که برای کار با واحد ADC، در صورت نیاز تنظیم می‌شود، NVIC یا تنظیم وقفه است. که در اینجا چون ما از DMA استفاده می‌کنیم، نیازی به تنظیم این بخش نیست.

سپس باید از تب DMA و کلید Add یک کانال از DMA را به ADC1 اختصاص دهیم. همچنین از بخش Mode در این تب، حالت انتقال اطلاعات را انتخاب می‌کنیم (در اینجا Circular انتخاب‌شده زیرا می‌خواهیم انتقال اطلاعات از ADC به‌طور پیوسته انجام شود).

بخش‌های Clock و Project Manager نیز مانند گذشته تنظیم می‌شوند.

 

مرحله دوم نوشتن کد پروژه

ابتدا باید کدهای مربوط به تنظیم و راه‌اندازی واحد ADC و DMA را بنویسیم. برای واحد ADC، به کدهای فعال‌سازی، کالیبره کردن، و استارت نرم‌افزاری تبدیل (و در صورت نیاز به فعال‌سازی وقفه) نیاز داریم:

ثابت مربوط به اندازه حافظه مورد نیاز و همچنین متغیرهای مورد استفاده را به کد اضافه می‌کنیم:

و سپس کدهای مربوط به تنظیم و شروع به کار DMA را می‌نویسیم:

با نوشتن این کد، آدرس اولین خانه حافظه موردنظر، و آدرس رجیستر مربوط به داده تبدیل‌شده توسط ADC1 تنظیم‌شده‌اند. همچنین مقدار اطلاعاتی که می‌خواهیم منتقل شوند (در اینجا 2) مشخص‌شده است.

اکنون می‌توانیم در بخش Debug و با تنظیم متغیر adc_read در watch1 مشاهده کنیم که مقادیر دو کانال 0 و 1 ADC پس از تبدیل در دو خانه حافظه که تعریف کرده‌ایم نوشته می‌شوند:

همچنین می‌توان این اطلاعات ذخیره شده در حافظه را از طریق واحد USART ارسال کرد، بدین منظور می‌توانیم کد زیر را در حلقه while(1) قرار دهیم:

خروجی در ترمینال :

خطاهای احتمالی

  • دستورات مربوط به تنظیم فعال‌سازی ADC و DMA، باید حتما در تابع int main و بعد از فراخوانی SystemClock_Config نوشته شود. در غیر این صورت، برنامه دچار خطا خواهد شد.
  • دقت شود که واحد ADC، حتما در مود Circular تنظیم شود. در غیر این صورت پس از یک بار تبدیل و یک بار پر شدن حافظه، اجرا متوقف خواهد شد و اطلاعات دیگری دریافت و در حافظه ثبت نمی‌شود.
  • دو تابع تنظیم آدرس و تنظیم مقدار داده‌هایی که باید منتقل شوند برای واحد DMA باید به‌درستی تنظیم شوند(مشابه کد ارائه‌شده)، زیرا در غیر این صورت واحد DMA راه‌اندازی نمی‌شود.

در بخش بعد با نحوه ارسال اطلاعات به وسیله USART و از طریق DMA آشنا خواهیم شد.

لینک پروژه در گیت هاب