DS1820 원와이어 온도 센서를 라즈베리 파이 GPIO로 연결하는 방법
라즈베리 파이로 실내 또는 실외 온도를 모니터링하는 것은 최소한의 설정으로 가능합니다. 이 가이드는 DS18S20(DS1820) 1-Wire 센서를 GPIO 핀에 직접 배선하고 소프트웨어로 온도를 읽고 RRDtool로 데이터를 로깅하는 방법을 보여줍니다.
라즈베리 파이와 1-Wire
DS18S20, DS18B20, DS1822는 모두 TO-92 패키지에 센서, ADC, 직렬 인터페이스를 결합한 1-Wire 온도 센서입니다. 핀아웃과 소프트웨어 인터페이스는 공유하지만 비용과 정확도에서 차이가 있습니다 – DS18S20은 ±0.5°C, DS18B20은 ±0.5°C, DS1822도 ±0.5°C 정확도를 가지지만 더 저렴합니다.
각 장치는 세 핀을 가집니다: 그라운드(GND, 핀 1), 데이터(DQ, 핀 2), 전원(VDD, 핀 3). 기생 전원 공급(3~5V)으로 데이터 라인의 풀업 저항만으로 센서에 전원을 공급할 수 있습니다.
단 하나의 저항만 필요
센서의 DQ 핀을 파이의 GPIO 4에 연결하세요. GND를 파이 그라운드에, VDD를 GND에 연결해 기생 전원 모드를 활성화하세요. 3.3V와 GPIO 4 사이에 4.7 kΩ 풀업 저항을 설치하세요. 작은 브레드보드나 직각 헤더로 배선을 깔끔하게 정리하면 파이 공식 케이스 안에 들어갑니다.
1-Wire 소프트웨어 드라이버
라즈비안(또는 데비안 기반 배포판)에서 커널 모듈 로드:
sudo modprobe w1-gpio pullup=1
sudo modprobe w1-therm
pullup=1 플래그는 센서가 풀업 저항을 통해 전원 공급됨을 드라이버에 알립니다. 로드 후 각 센서는 /sys/bus/w1/devices 아래 하위 디렉터리로 나타납니다. 디렉터리 이름은 패밀리 코드와 센서의 고유 64비트 식별자로 구성됩니다: DS18S20/DS1820은 패밀리 코드 10, DS18B20은 28, DS1822는 22를 사용합니다.
각 디렉터리 안의 w1_slave에는 두 줄이 있습니다. 첫 줄은 원시 레지스터 덤프와 CRC 체크. 둘째 줄은 t=xxxx로 끝나며 천 분의 1 도 섭씨 단위 온도입니다. 예:
cd /sys/bus/w1/devices
cd 10-000801b5*
cat w1_slave
0f 00 4b 46 ff ff 06 10 0c : crc=0c YES
0f 00 4b 46 ff ff 06 10 0c t=7375
값 7375는 7.375°C에 해당합니다. 데이터시트 지정 정확도 ±0.5°C이므로 실제 온도는 판독값의 ±0.5°C 이내입니다.
부팅 시 모듈 자동 로드를 위해 /etc/modules에 추가:
# /etc/modules
w1-gpio pullup=1
w1-therm
장기 저장과 시각화를 위해 RRDtool이 이상적입니다. 설치:
sudo apt-get install rrdtool python-rrdtool
15분마다 값을 기록하고 일일 집계를 10년간 유지하는 데이터베이스 정의:
rrdtool create temperature.rrd --step 900 \
DS:temp0:GAUGE:1200:-40:80 \
DS:temp1:GAUGE:1200:-40:80 \
RRA:AVERAGE:0.5:1:960 \
RRA:MIN:0.5:96:3600 \
RRA:MAX:0.5:96:3600 \
RRA:AVERAGE:0.5:96:3600
파이썬으로 데이터 수집
아래는 w1_slave를 읽고 RRDtool 데이터베이스에 값을 삽입하는 최소 파이썬 스크립트입니다. 센서 경로와 데이터베이스 파일명을 필요에 맞게 조정하세요.
import os
import rrdtool
W1_PATH = '/sys/bus/w1/devices'
DB_FILE = 'temperature.rrd'
def read_temp(sensor_id):
with open(f'{W1_PATH}/{sensor_id}/w1_slave') as f:
lines = f.readlines()
if lines[1].strip().endswith('YES'):
temp_milli = int(lines[1].strip().split('t=')[-1])
return temp_milli / 1000.0
return None
# 두 센서 예시
temps = {
'temp0': read_temp('10-000801b5'),
'temp1': read_temp('28-0000045e')
}
rrdtool.update(DB_FILE, ','.join(str(t) for t in temps.values()))
스크립트를 주기적(예: cron)으로 실행해 데이터베이스를 최신 상태로 유지하세요.