الرئيسية قاعدة المعرفة الكهرباء والإلكترون مشروع تطبيقي: تصميم وبناء وحدة مراقبة صناعية من PCB إلى البرنامج
الكهرباء والإلكترون

مشروع تطبيقي: تصميم وبناء وحدة مراقبة صناعية من PCB إلى البرنامج

نظرة عامة: وحدة مراقبة صناعية كاملة

في هذا الدرس الختامي، نبني مشروعاً يجمع كل ما تعلمناه: وحدة مراقبة صناعية تقرأ مستشعرات متعددة، تتواصل عبر Modbus RTU مع نظام SCADA، وترسل البيانات للسحابة عبر WiFi/MQTT.

مواصفات المشروع

  • قراءة 4 مستشعرات تناظرية (حرارة، تيار، ضغط، اهتزاز)
  • قراءة 4 مدخلات رقمية (حساسات قرب، نهايات مشوار)
  • التحكم بـ 4 مخرجات رقمية (مرحلات لمحركات وصمامات)
  • اتصال Modbus RTU كـ Slave عبر RS-485
  • إرسال بيانات عبر MQTT للمراقبة عن بعد
  • شاشة OLED محلية لعرض الحالة

اختيار المتحكم

نستخدم STM32F407 كمتحكم رئيسي (قراءة مستشعرات + Modbus) مع ESP32 كوحدة اتصال WiFi/MQTT. الفصل بينهما يزيد الموثوقية: حتى لو فشل WiFi، يستمر التحكم المحلي.

تصميم المخطط الإلكتروني: STM32 + مستشعرات + Modbus

دائرة التغذية

  • مدخل 24V DC صناعي (الجهد القياسي في المصانع)
  • منظم DC-DC يحوّل إلى 5V (لتغذية المرحلات والحساسات)
  • منظم LDO يحوّل 5V إلى 3.3V (لتغذية المتحكم)
  • مكثفات فلترة على كل منظم (100uF + 100nF)
  • حماية من عكس القطبية بديود أو MOSFET

دائرة المدخلات التناظرية

مستشعر 4-20mA ──── مقاومة 165Ω ──── ADC Pin
                                    │
                              مكثف 100nF
                                    │
                                   GND

مقاومة 165 أوم تحوّل تيار 4-20mA إلى جهد 0.66-3.3V المناسب لـ ADC. المكثف يرشح التشويش عالي التردد.

دائرة RS-485

STM32 UART TX ──── MAX485 DI
STM32 UART RX ──── MAX485 RO
STM32 GPIO    ──── MAX485 DE/RE  (التحكم بالاتجاه)
MAX485 A/B    ──── خط RS-485 الصناعي

تصميم لوحة PCB في KiCad

قواعد تصميم اللوحات الصناعية

  • عرض المسارات: 0.5mm كحد أدنى لإشارات المنطق، 1mm+ لمسارات القدرة
  • مستوى أرضي: طبقة أرضي كاملة تحت طبقة الإشارات لتقليل التشويش
  • فصل التناظري والرقمي: مسارات ADC بعيدة عن مسارات PWM والاتصالات
  • حماية ESD: ديودات TVS على جميع الموصلات الخارجية
  • نقاط تثبيت: 4 ثقوب M3 في الزوايا للتثبيت في علبة DIN Rail

ملفات الإخراج

  • Gerber: لتصنيع اللوحة
  • BOM (قائمة المكونات): بتنسيق CSV لطلب القطع
  • Pick-and-Place: لماكينة التجميع الآلي

كتابة البرنامج الثابت: قراءة ADC و UART و Modbus RTU

هيكل البرنامج

// main.c - الهيكل العام للبرنامج
#include "FreeRTOS.h"
#include "task.h"

// سجلات Modbus
#define MODBUS_ADDR 1
volatile uint16_t holding_regs[32];   // سجلات القراءة/الكتابة
volatile uint16_t input_regs[32];     // سجلات القراءة فقط

void sensor_task(void *p) {
    (void)p;
    MovingAverage filters[4];
    for (int i = 0; i < 4; i++) filter_init(&filters[i]);

    while (1) {
        for (int ch = 0; ch < 4; ch++) {
            uint16_t raw = filter_update(&filters[ch], read_adc_channel(ch));
            input_regs[ch] = raw;
        }
        // تحويل القيم الخام لوحدات هندسية
        input_regs[10] = (uint16_t)(ntc_to_celsius(input_regs[0]) * 10);
        input_regs[11] = (uint16_t)(raw_to_current(input_regs[1]) * 100);
        input_regs[12] = (uint16_t)(raw_to_pressure(input_regs[2]) * 10);
        input_regs[13] = (uint16_t)(raw_to_vibration(input_regs[3]) * 10);

        vTaskDelay(pdMS_TO_TICKS(50));
    }
}

معالجة Modbus RTU

#define MODBUS_BUF_SIZE 256

void modbus_task(void *p) {
    (void)p;
    uint8_t rx_buf[MODBUS_BUF_SIZE];

    while (1) {
        int len = uart_receive_frame(rx_buf, MODBUS_BUF_SIZE, 50);
        if (len < 4) continue;

        if (rx_buf[0] != MODBUS_ADDR) continue;
        if (!modbus_check_crc(rx_buf, len)) continue;

        uint8_t tx_buf[MODBUS_BUF_SIZE];
        int tx_len = 0;

        switch (rx_buf[1]) {
            case 0x03:  // Read Holding Registers
                tx_len = modbus_handle_read(rx_buf, tx_buf,
                    holding_regs, 32);
                break;
            case 0x04:  // Read Input Registers
                tx_len = modbus_handle_read(rx_buf, tx_buf,
                    input_regs, 32);
                break;
            case 0x06:  // Write Single Register
                tx_len = modbus_handle_write_single(rx_buf, tx_buf,
                    holding_regs, 32);
                break;
        }
        if (tx_len > 0) {
            rs485_set_tx_mode();
            uart_send(tx_buf, tx_len);
            rs485_set_rx_mode();
        }
    }
}

حساب CRC-16 لـ Modbus

uint16_t modbus_crc16(const uint8_t *data, uint16_t len) {
    uint16_t crc = 0xFFFF;
    for (uint16_t i = 0; i < len; i++) {
        crc ^= data[i];
        for (uint8_t j = 0; j < 8; j++) {
            if (crc & 0x0001)
                crc = (crc >> 1) ^ 0xA001;
            else
                crc >>= 1;
        }
    }
    return crc;
}

الاختبار والمعايرة

اختبار المستشعرات

// دالة معايرة: قراءتان معروفتان لحساب المعادلة الخطية
typedef struct {
    float slope;
    float offset;
} Calibration;

Calibration calibrate_linear(float raw1, float eng1,
                             float raw2, float eng2) {
    Calibration cal;
    cal.slope = (eng2 - eng1) / (raw2 - raw1);
    cal.offset = eng1 - cal.slope * raw1;
    return cal;
}

float apply_calibration(Calibration *cal, float raw) {
    return cal->slope * raw + cal->offset;
}

اختبار Modbus

استخدم برنامج Modbus Poll أو QModMaster على الحاسوب للتحقق من:

  • القراءة الصحيحة لسجلات Input Registers
  • الكتابة والقراءة لسجلات Holding Registers
  • الاستجابة الصحيحة للعناوين والدوال
  • التعامل مع الإطارات الخاطئة

اختبار التحمل

  • تشغيل الوحدة 72 ساعة متواصلة ومراقبة استقرار القراءات
  • اختبار انقطاع وعودة التغذية (Power Cycling)
  • اختبار أسوأ حالة حرارية (60 درجة مئوية)

من النموذج الأولي إلى الإنتاج

خطوات التصنيع

  1. مراجعة التصميم: مراجعة المخطط و PCB مع مهندس آخر
  2. طلب نماذج PCB: من مصنع مثل JLCPCB أو PCBWay
  3. تجميع يدوي: لحام المكونات والاختبار الأولي
  4. اختبار وظيفي: تشغيل جميع الاختبارات البرمجية
  5. تصميم العلبة: علبة DIN Rail بلاستيكية أو معدنية
  6. التجميع الآلي: عند الإنتاج بكميات (PCBA)

شهادات ومعايير

  • CE: إلزامي للبيع في أوروبا
  • IEC 61131-2: معيار أجهزة التحكم المبرمجة
  • EMC: اختبار التوافق الكهرومغناطيسي

مثال Rust: هيكل برنامج مدمج آمن

#![no_std]
#![no_main]

use cortex_m_rt::entry;
use stm32f4xx_hal::{pac, prelude::*, adc::Adc};

#[entry]
fn main() -> ! {
    let dp = pac::Peripherals::take().unwrap();
    let rcc = dp.RCC.constrain();
    let clocks = rcc.cfgr.sysclk(168.MHz()).freeze();

    let gpioa = dp.GPIOA.split();
    let adc_pin = gpioa.pa0.into_analog();
    let mut adc = Adc::adc1(dp.ADC1, true, Default::default());

    loop {
        let raw: u16 = adc.read(&adc_pin).unwrap();
        let voltage = (raw as f32 / 4095.0) * 3.3;
        // معالجة القراءة...
        cortex_m::asm::delay(8_000_000);
    }
}

الخلاصة والخطوات القادمة

في هذه السلسلة، تعلمنا أساسيات الأنظمة المدمجة من GPIO البسيط وحتى بناء وحدة مراقبة صناعية كاملة مع Modbus و MQTT. المفاهيم الأساسية التي غطيناها:

  • معمارية المتحكمات الدقيقة وأنواع الذاكرة
  • التعامل مع المدخلات والمخرجات الرقمية والتناظرية
  • بروتوكولات الاتصال UART و SPI و I2C
  • المؤقتات و PWM والتحكم PID
  • المقاطعات و FreeRTOS لتعدد المهام
  • ESP32 و WiFi و MQTT لإنترنت الأشياء الصناعي
  • تصميم وبناء نظام صناعي متكامل

للتعمق أكثر

  • Modbus TCP/IP: ربط وحدات المراقبة بشبكة Ethernet الصناعية
  • OTA Updates: تحديث البرنامج الثابت عن بعد
  • TinyML: تشغيل نماذج ذكاء اصطناعي على المتحكم للصيانة التنبؤية
  • Rust المدمج: بناء أنظمة آمنة من أخطاء الذاكرة باستخدام embedded-hal
  • تصميم PCB متقدم: لوحات متعددة الطبقات مع تحكم بالمعاوقة
project STM32 PCB-design Modbus firmware industrial-monitor مشروع تطبيقي تصميم اللوحة البرنامج الثابت المراقبة الصناعية موديس المتحكم