pthreads - Arduino 原型(prototype)线程的一些问题

标签 pthreads arduino sensors infrared

我正在做一个关于控制两个传感器(超声波和红外)的项目,并使用 Arduino 管理它们。 IR接收器内部有一个滤波器系统,因此它以 36 kHz 的频率接收。我使用模块 srf04 来处理超声波。如果我编写的程序只需要控制一个传感器,它就可以工作。但我必须将这两个信号插入一个结果。所以我使用了原型(prototype)线程!但它不起作用...错误是什么?

这是代码:

#include <pt.h>

int iro = 8, iri = 4, us = 12, distanza, us_vcc = 13, ir_vcc = 7;
long durata;

static struct pt pt1, pt2, pt3;

static int irthread(struct pt *pt) {
  PT_BEGIN(pt);
  while(1) {
    PT_WAIT_UNTIL(pt, 1>0);
    digitalWrite(iro, HIGH);
    delayMicroseconds(9);
    digitalWrite(iro, LOW);
    delayMicroseconds(9);
  }
  PT_END(pt);
}

static int usthread(struct pt *pt) {
  static unsigned long timer = 0;
  PT_BEGIN(pt);
  while(1) {
    PT_WAIT_UNTIL(pt, millis() - timer > 200);
    timer = millis();
    pinMode(us, OUTPUT);
    digitalWrite(us, LOW);
    delayMicroseconds(5);
    digitalWrite(us, HIGH);
    delayMicroseconds(10);
    digitalWrite(us, LOW);
    pinMode(us, INPUT);
    durata = pulseIn(us, HIGH);
    distanza = durata/58;
  }
  PT_END(pt);
}

static int leggithread(struct pt *pt) {
  static unsigned long timer = 0;
  PT_BEGIN(pt);
  while(1) {
    PT_WAIT_UNTIL(pt, millis() - timer > 200);
    timer = millis();
    Serial.print(distanza);
    Serial.print("cm ");
    if (digitalRead(iri) == LOW)
      Serial.println("ir si");
    else
      Serial.println("ir no");
  }
  PT_END(pt);
}

void setup() {
  pinMode(iro, OUTPUT);
  pinMode(iri, INPUT);
  pinMode(us_vcc, OUTPUT);
  digitalWrite(us_vcc, HIGH);
  pinMode(ir_vcc, OUTPUT);
  digitalWrite(ir_vcc, HIGH);
  Serial.begin(9600);

  PT_INIT(&pt1);
  PT_INIT(&pt2);
  PT_INIT(&pt3);
}

void loop() {
  irthread(&pt1);
  usthread(&pt2);
  leggithread(&pt3);
}

每个线程的单个代码部分都可以工作。

<小时/>

更新

我解决了我的问题(消除了irthread()),代码现在是这样的:

#include <pt.h>

int iro = 8, iri = 4, us = 12, distanza, us_vcc = 13, ir_vcc = 7;
long durata;

static struct pt pt1, pt2;

static int usthread(struct pt *pt) {
  static unsigned long timer = 0;
  PT_BEGIN(pt);
  while(1) {
    PT_WAIT_UNTIL(pt, millis() - timer > 200);
    timer = millis();
    pinMode(us, OUTPUT);
    digitalWrite(us, LOW);
    delayMicroseconds(5);
    digitalWrite(us, HIGH);
    delayMicroseconds(10);
    digitalWrite(us, LOW);
    pinMode(us, INPUT);
    durata = pulseIn(us, HIGH);
  }
  PT_END(pt);
}

static int leggithread(struct pt *pt) {
  static unsigned long timer = 0;
  PT_BEGIN(pt);
  while(1) {
    PT_WAIT_UNTIL(pt, millis() - timer > 200);
    timer = millis();
    distanza = durata/58;
    Serial.print(distanza);
    Serial.print("cm ");
    if(digitalRead(iri) == LOW)
      Serial.println("ir si");
    else
      Serial.println("ir no");
  }
  PT_END(pt);
}

void setup() {
  pinMode(iro, OUTPUT);
  tone(iro, 36000);
  pinMode(iri, INPUT);
  pinMode(us_vcc, OUTPUT);
  digitalWrite(us_vcc, HIGH);
  pinMode(ir_vcc, OUTPUT);
  digitalWrite(ir_vcc, HIGH);
  Serial.begin(9600);

  PT_INIT(&pt1);
  PT_INIT(&pt2);
}

void loop() {
  usthread(&pt1);
  leggithread(&pt2);
}

现在的问题是超声波传感器。如果我在没有原型(prototype)线程的单个程序中控制它,它可以到达 3 米距离的物体。现在,即使我把东西放在 1 米处,“距离”最大也为 15 厘米。错误是什么?

最佳答案

irthread()中,宏PT_WAIT_UNTIL的第二个参数始终计算为true:

PT_WAIT_UNTIL(pt, 1>0);

因此程序将陷入 irthread() 的无限循环中,因为在这种情况下宏 PT_WAIT_UNTIL 的部分结果类似于 if(!(1>0)) return 0;;语句 return 0 永远不会被调用。

<小时/>

它适用于 usthread()leggithread(),因为第二个参数在前 200 毫秒内为 false 并且变量被设置为在单次为 true 后的 200 毫秒内再次为 false。

一些背景信息位于 How protothreads really work

关于pthreads - Arduino 原型(prototype)线程的一些问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6230878/

相关文章:

c - 共享内存段被删除?

c++ - 如何使arduino无人机具有侧倾,俯仰和偏航值稳定?

java - 用于记录传感器数据的 Android 按钮

python - 连接到 TI Sensortag cc2541 的 Macbook Pro 2015

c - pthread_cancel() 使我的程序崩溃

c - 使用互斥锁按顺序同步线程

pthreads - 从多线程调用 MPI 函数

arduino - Digispark 读取大写锁定状态

python - pyserial - 如何读取从串行设备发送的最后一行

java - 如何检测Android手机的方向从水平位置到垂直位置的变化?