You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

树莓派NodeJS基于PIGPIO发送Wiegand数据接收不匹配问题求助

树莓派Node.js实现Wiegand协议发送数据异常问题

问题背景

在树莓派上使用PIGPIO库通过两路波形发送Wiegand协议数据,之前的C语言代码无法正常工作,改用Node.js开发后,发送的高低电平比特数组与接收端结果完全不匹配,怀疑是缓冲区发送逻辑问题,但不知道如何定位修复。

26位Wiegand数据示例

原始/反转比特串示例:

10000000100000000000000010
01000000000000000100000001

示例1

发送比特串:

10000000100000000000000010

接收结果:

[
  0, 0, 0, 1, 1,
  1, 1, 1, 1, 1,
  1
]

示例2

发送比特串:

01000000000000000100000001

接收结果:

[
  0, 0, 1, 1, 1,
  1, 1, 1, 1, 1,
  1
]

当前代码

const pigpio = require('pigpio');
const Gpio = pigpio.Gpio;
var dateNow= new Date()
var date = dateNow.getMilliseconds();

// 声明并初始化引脚
const outPin0 = 12;
const output0 = new Gpio(outPin0, {mode: Gpio.OUTPUT});
output0.digitalWrite(1);

const outPin1 = 13;
const output1 = new Gpio(outPin1, {mode: Gpio.OUTPUT}); 
output1.digitalWrite(1);
pigpio.waveClear();

// 初始化波形数组
let firstWaveForm = [];
let secondWaveForm = [];
let envio = [];

// let wiegand26bits= [1,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0];
let wiegand26bits= [0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1]

// 生成Wiegand 0引脚(绿色)的波形
let x = 0
for (wiegand26bits[x]; x < wiegand26bits.length; x++) {
  if (wiegand26bits[x]=== 0) {
    firstWaveForm.push({ gpioOn: outPin0, gpioOff: 0, usDelay: 1000});
    // firstWaveForm.push({ gpioOn: 0, gpioOff: outPin0, usDelay: 1000 });
  } else {
    firstWaveForm.push({ gpioOn: 0, gpioOff: outPin0, usDelay: 1000 });
    // firstWaveForm.push({ gpioOn: outPin0, gpioOff: 0, usDelay: 5000});
  }
}
console.log(firstWaveForm);
// 创建波形
pigpio.waveAddGeneric(firstWaveForm);
let firstWaveId = pigpio.waveCreate();
console.log(firstWaveId);

// 生成Wiegand 1引脚(白色)的波形
let y = 0
for (wiegand26bits[y]; y < wiegand26bits.length; y++) {
  if (wiegand26bits[y]!== 0) {
    secondWaveForm.push({ gpioOn: outPin1, gpioOff: 0, usDelay: 1000});
    // secondWaveForm.push({ gpioOn: 0, gpioOff: outPin1, usDelay: 1000});
  } else {
    secondWaveForm.push({ gpioOn: 0, gpioOff: outPin1, usDelay: 1000});
    // secondWaveForm.push({ gpioOn: outPin1, gpioOff: 0, usDelay: 1000});
  }
}
// 创建波形
pigpio.waveAddGeneric(secondWaveForm);
console.log(secondWaveForm);
let secondWaveId = pigpio.waveCreate();
console.log(secondWaveId);

// 构建波形链并重复一次
if (firstWaveId >= 0 && secondWaveId >= 0 && firstWaveForm.length == secondWaveForm.length)  {
  let chain = [firstWaveId, 255, 0,1, secondWaveId, 255, 0,1];
  pigpio.waveChain(chain);
}

// 等待波形发送完成
while (pigpio.waveTxBusy()) {}

// 清理波形资源
pigpio.waveDelete(firstWaveId);
pigpio.waveDelete(secondWaveId);
pigpio.waveClear();

问题分析与修复方案

核心问题

  1. Wiegand协议逻辑错误:Wiegand靠电平下降沿识别比特,默认状态是高电平,你的代码只设置了单方向电平变化,没有恢复初始高电平,接收端无法识别比特边界。
  2. 波形发送时序错误:你先发送完Pin0的所有波形再发Pin1的,但Wiegand两个引脚是同步工作的,每个比特的两个引脚状态需要同时变化,串行发送会导致时序完全混乱。
  3. 延迟参数不符合规范:Wiegand标准比特间隔是200-500us,你设置的1000us超出接收端识别窗口,导致丢包。

修复步骤

  1. 修正波形生成逻辑:每个比特需要包含“拉低电平+恢复高电平”两个阶段,触发接收端的下降沿识别:
    • 0比特:拉低Pin0 → 恢复高电平
    • 1比特:拉低Pin1 → 恢复高电平
      延迟设为200us符合标准。
  2. 同步生成两路波形:将两个引脚的波形合并到同一个数组,确保每个比特的电平变化同时发生。
  3. 简化波形发送流程:不需要分开创建两个波形,直接生成包含所有比特的单个波形,避免串行发送的时序问题。

修复后的代码

const pigpio = require('pigpio');
const Gpio = pigpio.Gpio;

// 初始化Wiegand引脚,默认高电平
const WIEGAND_D0 = 12;
const WIEGAND_D1 = 13;

const d0 = new Gpio(WIEGAND_D0, { mode: Gpio.OUTPUT });
const d1 = new Gpio(WIEGAND_D1, { mode: Gpio.OUTPUT });
d0.digitalWrite(1);
d1.digitalWrite(1);

pigpio.waveClear();

// 26位Wiegand数据
const wiegand26bits = [0,1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0,0,1];

const waveform = [];
const BIT_DELAY = 200; // 符合Wiegand标准的延迟

for (const bit of wiegand26bits) {
  // 拉低对应引脚触发比特
  if (bit === 0) {
    waveform.push({ gpioOff: WIEGAND_D0, gpioOn: 0, usDelay: BIT_DELAY });
  } else {
    waveform.push({ gpioOff: WIEGAND_D1, gpioOn: 0, usDelay: BIT_DELAY });
  }
  // 恢复高电平,准备下一个比特
  waveform.push({ gpioOn: WIEGAND_D0 | WIEGAND_D1, gpioOff: 0, usDelay: BIT_DELAY });
}

// 添加结束后的空闲状态
waveform.push({ gpioOn: WIEGAND_D0 | WIEGAND_D1, gpioOff: 0, usDelay: 1000 });

// 创建并发送波形
pigpio.waveAddGeneric(waveform);
const waveId = pigpio.waveCreate();

if (waveId >= 0) {
  pigpio.waveTxSend(waveId, pigpio.WAVE_MODE_ONE_SHOT);
  // 等待发送完成
  while (pigpio.waveTxBusy()) {}
  pigpio.waveDelete(waveId);
}

pigpio.waveClear();

额外注意事项

  • 确保接线正确:Wiegand D0接Pin12,D1接Pin13,若接收端无内置上拉电阻,需额外添加10kΩ上拉电阻。
  • 可用逻辑分析仪观察波形,确认每个比特的下降沿和电平恢复是否符合标准。

内容的提问来源于stack exchange,提问作者Alan Chavez

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.20 11:51:32