I2C 주소 충돌과 배선 불량, 같은 먹통을 가르는 진단법

profile_image
작성자 버스추적자현우
댓글 0건 조회 6회

센서 하나는 잘 읽히는데 두 번째 모듈을 연결하는 순간 값이 멈추거나, I2C 스캐너에서 장치가 나타났다 사라진다면 어디부터 의심해야 할까요? 이런 증상은 흔히 I2C 주소 충돌로 단정되지만, 실제 현장에서는 SDA·SCL 배선 불량, 전압 불일치, 과도한 풀업, 전원 강하도 거의 같은 모습으로 나타납니다.

원인을 구분하지 않고 코드를 바꾸기 시작하면 정상인 라이브러리만 여러 번 교체하게 됩니다. 이 글은 아두이노와 라즈베리파이 기반의 센서 연결에서 주소 문제와 물리 계층 문제를 빠르게 가려내고, 재발하지 않도록 회로와 임베디드 코드를 손보는 순서에 집중합니다.

I2C 주소 충돌과 배선 불량은 증상부터 다릅니다

장치를 한 개씩 연결하면 첫 단서가 보입니다

I2C 버스가 먹통이 되었을 때 가장 먼저 할 일은 스케치 수정이 아니라 모듈을 한 개씩 분리해 다시 연결하는 것입니다. 센서 A만 연결했을 때 정상이고 센서 B만 연결해도 정상인데 둘을 함께 연결할 때만 실패한다면 주소 충돌 가능성이 높습니다. 반대로 특정 모듈은 단독 연결 상태에서도 검색되지 않거나 손으로 케이블을 건드릴 때 주소가 나타난다면 배선과 납땜 상태를 먼저 봐야 합니다.

주소 충돌은 대체로 재현성이 높습니다. 전원을 껐다 켜도 두 장치를 동시에 연결한 조건에서 같은 문제가 반복됩니다. 배선 불량은 부팅할 때마다 결과가 달라지거나, 0x00·0x7F처럼 정상 장치 주소로 보기 어려운 값이 검색되고, 통신 도중 멈추는 양상을 보이기 쉽습니다. 온도나 케이블 위치에 따라 증상이 달라지는 것도 접촉 불량과 신호 무결성 문제의 단서입니다.

아두이노가 처음이라면 보드와 개발 환경의 기본 개념을 설명한 아두이노 지식백과 항목을 함께 확인해도 좋습니다. 다만 보드가 정상적으로 업로드된다는 사실만으로 I2C 핀 배치까지 올바르다고 판단해서는 안 됩니다. Uno 계열과 Mega, ESP32, 일부 호환 보드는 SDA와 SCL 위치 또는 기본 핀 설정이 서로 다릅니다.

  • 두 모듈 모두 단독으로 정상: 동일 주소, 버스 부하, 전원 용량을 순서대로 의심합니다.
  • 한 모듈만 단독으로 실패: 해당 모듈의 전원, GND, 커넥터 방향과 납땜을 점검합니다.
  • 케이블을 움직이면 결과가 변함: 점퍼선 단선이나 브레드보드 접촉 불량 가능성이 큽니다.
  • 주소는 보이지만 데이터가 이상함: 잘못된 드라이버, 레지스터 설정, 전압 레벨을 확인합니다.
  • 통신 시작 후 전체 버스가 멈춤: 특정 장치가 SDA를 낮게 붙잡는 버스 고착을 의심합니다.

증상표로 진단 방향을 좁혀봅니다

같은 ‘센서 먹통’이라도 관찰 지점을 세분화하면 불필요한 부품 교체를 줄일 수 있습니다. 아래 표에서 한 가지 원인만 고르기보다 현재 현상과 가장 많이 일치하는 행을 찾고, 다음 섹션의 측정 순서로 검증해 보세요.

관찰한 현상우선 의심할 원인첫 확인 방법
같은 모델 두 개를 함께 연결하면 실패고정 I2C 주소 충돌각 모듈을 단독 스캔해 주소 비교
스캔할 때마다 주소 개수가 달라짐배선·전원·풀업 문제전압 측정 후 짧은 선으로 교체
낮은 속도에서는 정상, 고속에서 오류버스 용량 또는 파형 열화클록을 100kHz 이하로 내려 재시험
센서 추가 후 보드가 재부팅됨전원 강하 또는 단락부팅 순간 전압과 소비 전류 확인
주소는 검색되지만 값이 모두 동일주소 충돌 또는 코드 객체 공유주소별 객체와 초기화 순서 확인
현장 팁: ‘어제까지 됐다’는 말은 원인 배제의 근거가 아닙니다. 점퍼선, 브레드보드 접점, USB 전원은 이동과 온도 변화만으로도 상태가 달라질 수 있습니다.

스캐너보다 먼저 전압과 핀 상태를 확인합니다

전원을 끈 상태에서 연결을 다시 읽습니다

I2C 진단은 반드시 전원을 끈 뒤 회로의 연결 구조를 눈으로 확인하는 단계에서 시작합니다. VCC와 GND가 뒤바뀌지 않았는지, SDA와 SCL을 서로 바꾸지 않았는지, 마이크로컨트롤러와 센서가 공통 GND를 공유하는지 살펴보세요. 센서 모듈에 VIN과 3V3 핀이 모두 있다면 회로도나 판매 문서를 확인하지 않은 채 임의로 선택하면 안 됩니다. VIN에는 레귤레이터가 연결되고 3V3은 칩 전원에 직결된 제품도 있기 때문입니다.

전원을 넣은 다음 멀티미터로 보드의 3.3V 또는 5V 레일을 측정합니다. 무부하 전압만 보지 말고 센서를 모두 연결한 상태에서도 확인해야 합니다. 표시 전압이 정상이어도 통신 순간 짧게 내려가는 현상은 일반 멀티미터에 잡히지 않을 수 있으므로, 센서 추가 직후 보드가 재부팅되거나 값이 튄다면 오실로스코프 또는 로직 분석기를 활용하는 편이 정확합니다.

I2C의 SDA와 SCL은 오픈드레인 방식이라 장치가 선을 직접 높은 상태로 밀어 올리기보다 풀업 저항이 HIGH를 만듭니다. 따라서 유휴 상태에서 두 선의 전압은 대체로 해당 버스의 논리 전압 근처여야 합니다. 한 선이 계속 0V에 머문다면 코드보다 먼저 단락, 뒤집힌 모듈, 고착된 슬레이브를 분리해 찾아야 합니다.

  1. USB와 외부 어댑터를 모두 분리하고 VCC·GND·SDA·SCL 연결을 종이에 적습니다.
  2. 마이크로컨트롤러만 켜서 전원 레일과 SDA·SCL 유휴 전압을 측정합니다.
  3. 센서를 하나씩 추가하며 전압이 급격히 변하는 지점을 기록합니다.
  4. 문제가 생긴 모듈은 새 점퍼선과 다른 브레드보드 위치에서 단독 시험합니다.
  5. 모든 모듈이 단독으로 통과한 뒤에만 전체 버스를 다시 구성합니다.

풀업 저항은 많을수록 좋은 부품이 아닙니다

시판 센서 모듈에는 4.7kΩ 또는 10kΩ 풀업 저항이 이미 실장된 경우가 많습니다. 모듈 네 개를 병렬로 연결하면 저항도 병렬이 되어 합성 저항이 크게 낮아집니다. 예를 들어 4.7kΩ 풀업 네 개는 약 1.18kΩ이 되며, 장치가 LOW를 만들 때 더 큰 전류를 흘려야 합니다. 그 결과 일부 센서는 낮은 전압을 충분히 만들지 못해 간헐적인 NACK나 잘못된 비트가 발생할 수 있습니다.

반대로 풀업 저항값이 지나치게 크면 케이블과 입력 핀의 정전용량 때문에 상승 시간이 길어집니다. 짧은 브레드보드 배선과 100kHz에서는 동작해도 400kHz, 긴 리본 케이블, 여러 커넥터가 결합되면 HIGH 판정 전에 다음 클록이 시작될 수 있습니다. 처음에는 100kHz와 짧은 배선으로 안정성을 확보한 뒤 속도를 올리는 순서가 안전합니다.

3.3V 센서를 5V 아두이노에 연결할 때도 풀업이 어느 전압에 물려 있는지 반드시 확인하세요. 센서 모듈의 VCC를 3.3V로 공급했더라도 보드 쪽 풀업이 5V에 연결되어 있으면 SDA와 SCL은 5V까지 올라갈 수 있습니다. 센서가 5V 입력 허용 제품인지 확인할 수 없다면 양방향 레벨 시프터를 사용하거나 버스 전체를 3.3V 논리로 통일하는 편이 낫습니다.

  • 모듈 후면의 ‘472’, ‘103’ 표기를 찾아 내장 풀업 여부를 확인합니다.
  • 전원을 끈 상태에서 SDA와 VCC 사이 저항을 측정해 전체 합성 저항을 추정합니다.
  • 문제 재현 중에는 배선을 20cm 이하로 줄이고 분기선을 최소화합니다.
  • 레벨 시프터를 쓴다면 양쪽 전원과 공통 GND가 올바른지 확인합니다.
  • 로직 분석기에서 상승 모서리가 완만하면 속도와 버스 용량을 함께 낮춥니다.

주소 스캔과 장치 분리로 충돌 원인을 확정합니다

한 번의 스캔보다 조건별 기록이 중요합니다

전기적 상태가 정상으로 확인된 뒤 I2C 스캐너를 실행합니다. 스캐너는 0x08부터 0x77 범위에 주소를 보내고 응답 여부를 표시하는 간단한 도구지만, 한 번 검색됐다는 사실이 센서 전체 기능의 정상 동작을 보장하지는 않습니다. 주소 응답은 되면서 데이터 레지스터 읽기에서 실패하는 장치도 있기 때문입니다.

센서 A 단독, 센서 B 단독, A와 B 동시 연결의 세 조건을 각각 세 번 이상 시험하고 결과를 적어두세요. A와 B가 단독 상태에서 모두 0x76으로 잡히고 동시 연결에서도 0x76 하나만 보인다면 주소 충돌이 사실상 확인됩니다. 반면 단독 주소부터 흔들린다면 충돌보다 배선이나 전원 문제가 아직 해결되지 않은 것입니다.

스캐너 결과가 전혀 없을 때는 사용 중인 보드의 Wire 초기화 방식도 확인해야 합니다. 일부 마이크로컨트롤러는 기본 핀 대신 Wire.begin(SDA, SCL)처럼 핀을 명시해야 하며, 라즈베리파이는 운영체제 설정에서 I2C 인터페이스를 활성화해야 합니다. 개발 도구와 장치 제어 코드의 관계가 낯설다면 디바이스 드라이버 통합개발환경의 개요도 개념을 구분하는 데 도움이 됩니다.

  1. 모든 센서를 분리한 뒤 스캐너가 정상적으로 실행되는지 확인합니다.
  2. 첫 번째 센서만 연결해 검색 주소와 성공 횟수를 기록합니다.
  3. 두 번째 센서만 같은 선 길이와 전원 조건으로 시험합니다.
  4. 두 센서를 함께 연결하고 주소 개수, 검색 시간, 오류 메시지를 비교합니다.
  5. 버스 속도를 100kHz에서 50kHz로 낮춰 결과가 달라지는지 확인합니다.
  6. 주소가 같고 속도 변화와 무관하게 충돌하면 하드웨어 주소 변경 방법을 찾습니다.

주소 핀, 점퍼와 멀티플렉서의 선택 기준

주소 충돌이 확인되면 센서 데이터시트에서 ADDR, AD0, SDO, SA0 같은 주소 선택 핀을 찾습니다. 모듈에 납땜 점퍼가 있다면 패턴을 끊거나 브리지를 연결해 주소를 바꿀 수 있습니다. 여기서 주의할 점은 점퍼 옆에 인쇄된 주소가 7비트 주소인지, 읽기·쓰기 비트까지 포함한 8비트 표기인지 확인하는 것입니다. Arduino Wire 라이브러리는 일반적으로 7비트 주소를 사용하므로 데이터시트의 8비트 주소를 그대로 넣으면 통신하지 않습니다.

주소 변경 범위가 두 개뿐인데 같은 센서가 세 개 이상 필요하다면 TCA9548A 같은 I2C 멀티플렉서를 고려할 수 있습니다. 멀티플렉서는 동일 주소 장치를 서로 다른 채널로 분리하므로 기존 센서 라이브러리를 크게 바꾸지 않고 확장하기 좋습니다. 보급형 모듈은 판매처와 품질에 따라 대략 수천 원대에서 구할 수 있지만, 커넥터 품질과 전압 호환 여부를 먼저 확인해야 합니다.

소프트웨어 I2C로 별도 버스를 만드는 방법도 있습니다. 핀 여유가 있고 통신 속도가 낮은 프로젝트에는 경제적이지만, 타이밍을 소프트웨어로 처리하므로 다른 인터럽트와 충돌하거나 CPU 점유가 커질 수 있습니다. 장시간 운영하는 사물인터넷 장치라면 초기 비용이 조금 들더라도 하드웨어 버스 또는 멀티플렉서로 구조를 명확히 나누는 편이 유지보수에 유리합니다.

해결 방식장점주의점어울리는 상황
주소 핀 변경비용과 코드 변경이 적음선택 가능한 주소 수가 제한됨동일 센서 두 개 사용
I2C 멀티플렉서동일 주소 장치를 여러 개 분리채널 선택 코드와 부품 추가센서 수가 많거나 모듈 교체가 잦음
두 번째 하드웨어 버스버스 장애를 물리적으로 격리지원 보드와 추가 핀이 필요ESP32 등 다중 컨트롤러 지원 보드
소프트웨어 I2C남는 GPIO를 자유롭게 활용속도·타이밍·라이브러리 제약저속 시제품과 일회성 실험
설계 팁: 주소를 바꾼 뒤에는 회로도와 코드에 ‘센서 이름-주소-채널’을 함께 기록하세요. 숫자 하나만 주석에 남기면 모듈을 교체한 뒤 충돌이 재발하기 쉽습니다.

충돌 해결보다 버스를 나누는 편이 나을 때도 있습니다

복구 코드가 현장 고장을 줄여줍니다

주소와 배선을 고쳤더라도 센서가 순간적인 노이즈나 전원 변동으로 SDA를 LOW에 고정하면 전체 I2C 통신이 멈출 수 있습니다. 실험실에서는 재부팅으로 끝나지만 천장, 온실, 야외 함체에 설치한 사물인터넷 장치라면 사람이 전원을 껐다 켜기 어렵습니다. 따라서 임베디드 개발 단계에서 타임아웃과 재시도 횟수, 실패 장치 격리 정책을 미리 정해야 합니다.

센서 읽기 함수가 무한히 기다리지 않도록 제한 시간을 두고, 연속 실패 횟수가 기준을 넘으면 해당 센서만 재초기화합니다. 그래도 회복되지 않으면 SCL을 수차례 토글해 슬레이브가 남은 비트를 내보내게 한 뒤 STOP 조건을 생성하는 버스 복구 절차를 적용할 수 있습니다. 단, 사용하는 마이크로컨트롤러의 I2C 주변장치와 핀 모드 전환 방식을 확인한 뒤 구현해야 합니다.

전원을 개별 제어할 수 있는 로드 스위치나 MOSFET을 센서 전원에 추가하면 고착된 모듈만 재부팅할 수 있습니다. 다만 SDA와 SCL을 통해 전원이 역으로 유입되는 백파워링이 발생할 수 있으므로 단순히 VCC만 끄면 충분한지 시험해야 합니다. 운영 로그에는 주소, 오류 코드, 재시도 횟수, 복구 소요 시간을 남겨야 원격에서 주소 충돌과 일시적 노이즈를 구분할 수 있습니다.

  • 1회 실패: 짧은 간격을 두고 같은 레지스터 읽기를 재시도합니다.
  • 연속 실패: 센서 초기화 명령과 장치 식별 레지스터를 다시 확인합니다.
  • 버스 전체 고착: SCL 토글과 STOP 생성 후 I2C 주변장치를 재초기화합니다.
  • 복구 불가: 문제 채널 또는 센서 전원을 차단하고 나머지 기능을 유지합니다.
  • 반복 발생: 오류 시각과 온도, 전원 전압, 동작 중인 부하를 로그로 비교합니다.

모든 센서를 한 버스에 모으는 것이 항상 최선은 아닙니다

I2C는 적은 핀으로 여러 센서를 연결할 수 있다는 점이 매력적이지만, 그래서 모든 장치를 한 쌍의 선에 넣어야 하는 것은 아닙니다. 한 센서의 고장이 전체 시스템을 멈추게 한다면 핀 절약으로 얻은 이익보다 장애 범위가 더 커집니다. 특히 모터 드라이버 주변의 센서, 긴 케이블로 연결한 외부 센서, 안전 기능에 관여하는 센서는 내부의 짧은 버스와 분리할 가치가 있습니다.

반대 의견도 있습니다. 버스를 여러 개로 나누면 커넥터와 레벨 시프터, 멀티플렉서가 늘어나 회로가 복잡해지고 고장 지점도 많아진다는 주장입니다. 실제로 10cm 안쪽의 짧은 배선, 동일한 전압, 주소 변경이 가능한 센서 두세 개라면 단일 I2C 버스가 더 단순하고 경제적입니다. 중요한 것은 장치 수가 아니라 배선 길이, 전기적 환경, 장애가 미치는 범위입니다.

따라서 시제품에서는 한 버스로 빠르게 기능을 검증하되, 실제 설치 환경에서는 외부 센서와 내부 센서의 장애 영역을 따로 평가해 보세요. 같은 주소 장치가 많거나 케이블을 현장에서 자주 탈착한다면 멀티플렉서가 유리하고, 노이즈가 심한 장거리 구간이라면 I2C 연장만 고집하기보다 차동형 인터페이스나 별도 마이크로컨트롤러를 두는 방안도 검토할 만합니다. ‘주소만 바꾸면 끝’이라는 접근보다, 한 장치가 멈췄을 때 나머지 프로젝트가 계속 동작하는지를 설계 기준으로 삼는 편이 더 현실적입니다.

  • 책상 위 시제품은 짧은 단일 버스로 구성해 코드와 센서 기능을 먼저 검증합니다.
  • 외부로 나가는 케이블은 내부 PCB 배선과 다른 장애 구역으로 취급합니다.
  • 중요 센서는 보조 센서와 다른 채널 또는 다른 하드웨어 버스에 배치합니다.
  • 커넥터 탈착이 잦다면 핫플러그 순간의 전압과 버스 고착도 시험합니다.
  • 최종 판단은 핀 수보다 고장 복구 시간과 유지보수 비용을 기준으로 내립니다.
댓글목록

등록된 댓글이 없습니다.