ARDUINO 시작

김준혁·2026년 3월 24일

m 밀리 (milli) 10310^{-3} 1mm (미리미터)
μ 마이크로 (micro) 10610^{-6} 머리카락 굵기 정도
n 나노 (nano) 10910^{-9} DNA 분자 크기 수준
p 피코 (pico) 101210^{-12} 원자 크기 수준
LED 속에 커다란게 -임
PNP트랜지스터: 전기를 주면 꺼짐, 뺏으면 켜짐.
NPN트랜지스터: 전기를 주면(High) 켜짐, 뺏으면 꺼짐.
RISC: 코드가 길은만큼 전력소모 감소.
CISC: 코드가 짧은만큼 많은 기능을 함-> 전력소모 증가
ROM: 전원이 꺼져도 저장, 저장할 때
RAM: 전원이 꺼지면 날라감, 변수나 계산할 때
EEPROM(flash rom): ROM의 종류, RAM의 장점도 가져옴. 데이터 변경 가능.
FET(Field Effect Transistor)

  • '전압'으로 '전류'를 제어
    Capacitor: 축전기
    Diode: 전기가 한쪽 방향으로만 흐름

platfromio
.elf or .hex 파일이있으면 아두이노에 구울 수 있음.
volatile키워드를 써서 레지스터 주소에 접근할 수 있음.

#include <Arduino.h> // PlatformIO에서는 이 헤더가 필수입니다.

void setup() {
  // DDRB 레지스터 주소 (0x24) 직접 접근 -> 5번 비트 출력 설정
  *((volatile unsigned char *)0x24) |= 0x20; //2진수로 0010 0000

}

void loop() {
  // PORTB 레지스터 (0x25) -> LED ON
  *((volatile unsigned char *)0x25) |= 0x20;
  
  delay(1000);

  // PORTB 레지스터 (0x25) -> LED OFF
  *((volatile unsigned char *)0x25) &= ~0x20;
  
  delay(1000);
}

다른 방식으로 LED 켜보기(C)

#include <Arduino.h>

// 1. LED 상태를 보관할 구조체 정의
typedef struct {
    uint8_t pin;               // 핀 번호
    unsigned long onTime;      // 켜져 있을 시간 (ms)
    unsigned long offTime;     // 꺼져 있을 시간 (ms)
    uint8_t state;             // 현재 상태 (HIGH/LOW)
    unsigned long prevMillis;  // 마지막으로 상태가 바뀐 시간
} Flasher;

// 2. 구조체 초기화 함수 (C++의 생성자 역할)
void Flasher_Init(Flasher* f, uint8_t pin, unsigned long on, unsigned long off) {
    f->pin = pin;
    f->onTime = on;
    f->offTime = off;
    f->state = LOW;
    f->prevMillis = 0;
    
    pinMode(f->pin, OUTPUT);
}

// 3. 상태 업데이트 함수 (구조체 포인터를 받아 상태 변경)
void Flasher_Update(Flasher* f, unsigned long currentMillis) {
    // 켜져 있고, 끄는 시간이 되었을 때
    if ((f->state == HIGH) && (currentMillis - f->prevMillis >= f->onTime)) {
        f->state = LOW;
        f->prevMillis = currentMillis;
        digitalWrite(f->pin, f->state);
    }
    // 꺼져 있고, 켜는 시간이 되었을 때
    else if ((f->state == LOW) && (currentMillis - f->prevMillis >= f->offTime)) {
        f->state = HIGH;
        f->prevMillis = currentMillis;
        digitalWrite(f->pin, f->state);
    }
}

// 구조체 변수(인스턴스) 선언
Flasher led1;
Flasher led2;
Flasher led3;

void setup() {
    // 각 LED 초기화 (주소 전달 연산자 '&' 사용)
    Flasher_Init(&led1, 13, 1000, 1000);   // 13번 핀
    Flasher_Init(&led2, 12, 500, 500);   // 12번 핀
    Flasher_Init(&led3, 11, 100, 100);    // 11번 핀
}

void loop() {
    // 성능 최적화: loop 한 번당 millis()는 한 번만 호출하여 전달
    unsigned long currentMillis = millis(); 
    
    // 각 LED 상태 업데이트
    Flasher_Update(&led1, currentMillis);
    Flasher_Update(&led2, currentMillis);
    Flasher_Update(&led3, currentMillis);
    
    // 이 위치에 지연 없이 다른 작업 추가 가능
}

C++

#include <Arduino.h>

// LED 상태를 관리하는 클래스 정의
class Flasher {
  private:
    uint8_t ledPin;               // 제어할 핀 번호
    unsigned long OnTime;         // 켜져 있을 시간 (ms)
    unsigned long OffTime;        // 꺼져 있을 시간 (ms)
    
    int ledState;                 // 현재 LED 상태 (HIGH/LOW)
    unsigned long previousMillis; // 상태가 마지막으로 바뀐 시간

  public:
    // 생성자: 핀 번호 및 주기 설정
    Flasher(int pin, unsigned long on, unsigned long off) {
        ledPin = pin;
        OnTime = on;
        OffTime = off;
        
        ledState = LOW;
        previousMillis = 0;
        
        pinMode(ledPin, OUTPUT);
    }

    // 상태 업데이트 함수 (loop에서 지속 호출)
    void update() {
        // 현재 시간 확인
        unsigned long currentMillis = millis(); 

        // LED가 켜져 있고, 설정한 켜짐 시간(OnTime)이 지났을 때
        if ((ledState == HIGH) && (currentMillis - previousMillis >= OnTime)) {
            ledState = LOW;                  // 상태를 LOW로 변경
            previousMillis = currentMillis;  // 현재 시간을 과거 시간으로 저장
            digitalWrite(ledPin, ledState);  // 실제 핀 제어
        }
        // LED가 꺼져 있고, 설정한 꺼짐 시간(OffTime)이 지났을 때
        else if ((ledState == LOW) && (currentMillis - previousMillis >= OffTime)) {
            ledState = HIGH;                 // 상태를 HIGH로 변경
            previousMillis = currentMillis;  // 현재 시간을 과거 시간으로 저장
            digitalWrite(ledPin, ledState);  // 실제 핀 제어
        }
    }
};

// 독립적인 주기를 가진 객체 생성
// led1: 13번 핀, 100ms 켜지고 400ms 꺼짐 (빠르게 깜빡임)
Flasher led1(13, 100, 400);

// led2: 12번 핀, 500ms 켜지고 500ms 꺼짐 (느리게 깜빡임)
Flasher led2(12, 500, 500);

// led3: 11번 핀, 50ms 켜지고 950ms 꺼짐 (1초에 한 번 짧게 깜빡임)
Flasher led3(11, 50, 950);

void setup() {
    // 핀 초기화는 객체 생성 시 수행되므로 생략 가능
}

void loop() {
    // 1. 각 LED의 상태 업데이트
    // 내부적으로 millis()를 검사하여 시간이 된 객체만 상태를 반전시킴
    led1.update();
    led2.update();
    led3.update();
    
    // 2. 다른 작업 추가
    // delay()가 없으므로 센서 읽기, 통신 등의 작업을 자유롭게 배치 가능
}

TaskScheduler라이브러리 이용

#include <Arduino.h>
#include <TaskScheduler.h>

Scheduler runner;

// 태스크 콜백 함수 선언
void blinkLED1();
void blinkLED2();

// 태스크 객체 생성 (주기ms, 반복횟수, 콜백함수, 스케줄러포인터, 자동시작)
Task task1(1000, TASK_FOREVER, &blinkLED1, &runner, true); // 1초 주기
Task task2(300, TASK_FOREVER, &blinkLED2, &runner, true);  // 0.3초 주기

void blinkLED1() {
    digitalWrite(13, !digitalRead(13)); // 내장 LED 토글
}

void blinkLED2() {
    digitalWrite(12, !digitalRead(12)); // 외부 LED 토글
}

void setup() {
    pinMode(13, OUTPUT);
    pinMode(12, OUTPUT);
    runner.startNow(); // 스케줄러 시작
}

void loop() {
    runner.execute(); // 스케줄러 실행 루프 (delay 사용 금지)
}
profile
임베디드 개발자

0개의 댓글