Git Product home page Git Product logo

pigpio's People

Contributors

acschaefer avatar bennuttall avatar bjoernsch avatar btpankow avatar creavalix avatar drkmsmithjr avatar flaviut avatar foreignmeloman avatar gertrozing avatar guymcswain avatar hazuki0x0 avatar jaessy77 avatar jdiamond avatar joan2937 avatar joeyparrish avatar jonas-schievink avatar jul3k avatar maihde avatar maitredede avatar mathias-luedtke avatar mausy5043 avatar maxnet avatar miccoli avatar noviv avatar pbanasik avatar phlipped avatar plauche avatar slysven avatar theraspydev avatar thuffir avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

pigpio's Issues

tick values in notifications

The test program below sets the sample rate to 1µs, starts hardware PWM on GPIO18, and starts notifications on GPIO18. The PWM frequency is 200,000Hz and the duty cycle is 50%. The period for each PWM pulse is therefore 5µs.

The test program examines the tick and seqno fields in each notification. The seqno field is always correct, i.e., it's always 1 more than the seqno from the previous notification.

However, the tick field can have values that I don't understand. When the tick fields in two consecutive notifications are compared, the following can be observed:

  • The tick field in the first notification received can be greater than the tick field in the second notification received by a small number of microseconds. Typically 1 to 3 microseconds.
  • The tick field in two consecutive notifications can have the same value.
  • The tick field in two consecutive notifications can differ by up to 23µs.

Given that the sample rate is 1µs and the PWM period is 5µs, why is this happening?

#include <fcntl.h>
#include <stdio.h>
#include <pigpio.h>

#define LED 18
#define COUNT 1000

int main() {
  int version;
  int handle;
  char pipePath[32];
  int fd;
  int bytes;
  uint32_t notificationCount = 0;
  gpioReport_t r[COUNT];
  uint16_t lastSeqno = 0xffff;
  uint32_t lastTick;
  uint32_t minTickDiff = 0xffffffff;
  uint32_t maxTickDiff = 0;
  uint32_t seqnoErrors = 0;
  uint32_t tickErrors = 0;
  int entries;
  int i;

  gpioCfgClock(1, 1, 1);

  if ((version = gpioInitialise()) < 0) {
    printf("gpioInitialise error\n");
    return -1;
  }

  printf("version: %d\n", version);

  if (gpioHardwarePWM(LED, 200000, 500000) < 0) {
    printf("gpioHardwarePWM error\n");
    return -1;
  }

  if ((handle = gpioNotifyOpen()) < 0) {
    printf("gpioNotifyOpen error\n");
    return -1;
  }

  if (gpioNotifyBegin(handle, (1 << LED)) < 0) {
    printf("gpioNotifyBegin error\n");
    return -1;
  }

  sprintf(pipePath, "/dev/pigpio%d", handle);

  if ((fd = open(pipePath, O_RDONLY)) < 0) {
    printf("open error\n");
    return -1;
  }

  for (;;) {
    bytes = read(fd, r, 12*COUNT);

    if (bytes <= 0) {
      printf("read error\n");
      return -1;
    }

    entries = bytes / 12;

    for (i = 0; i != entries; ++i) {
      if (((uint16_t) (lastSeqno + 1)) != r[i].seqno) {
        printf("sequence error - lastSeqno: %d, seqno: %d\n", lastSeqno, r[i].seqno);
        seqnoErrors++;
      }

      if (notificationCount > 0) {
        if (r[i].tick < lastTick) {
          printf("tick error - tick %u < lastTick\n", lastTick - r[i].tick);
          tickErrors++;
        } else {
          if (r[i].tick - lastTick < minTickDiff) {
            minTickDiff = r[i].tick - lastTick;
          }

          if (r[i].tick - lastTick > maxTickDiff) {
            maxTickDiff = r[i].tick - lastTick;
          }
        }
      }

      ++notificationCount;
      if (notificationCount % 1000000 == 0) {
        printf("notificationCount: %u\n", notificationCount);
        printf("seqnoErrors: %u\n", seqnoErrors);
        printf("tickErrors: %u\n", tickErrors);
        printf("minTickDiff: %u\n", minTickDiff);
        printf("maxTickDiff: %u\n", maxTickDiff);
        printf("\n");

        minTickDiff = 0xffffffff;
        maxTickDiff = 0;
      }

      lastSeqno = r[i].seqno;
      lastTick = r[i].tick;
    }
  }

  gpioTerminate();

  return 0;
}

Alert thread lagging behind

We are currently trying to use the code from the rotary encoder example (http://abyz.co.uk/rpi/pigpio/ex_rotary_encoder.html) to read a position for PID control. The control loop is running in the main thread.

The issue we came across now is that sometimes, the alert callbacks do not get called for a very long time before being processed in a burst. This gives us uncontrollable errors in control which could lead to physical damage to our setup.

We are using a custom version of raspbian with the preemt-rt kernel patch and use the gpioCfgSetInternals(PI_CFG_RT_PRIORITY); to enable realtime processing. One possible problem with this seems to be the fact that there is no priority configuration for the single threads, so setting the alert thread on a higher priority is a solution we considered, but unfortunately there is no config option for this. Also, as the Pi2 has a quad core processor, it should be possible for the main thread and the alert thread to run in parallel.

pigpiod + wiegand = incorrect read

I have the keys wiegand with number (read and verify in other devices) and these numbers are written on the keys themselves:
0009030510
0009487621
0009236067
0009328295
I am git clone pigpiod library, maked and installed
I use modified example: /pigpio/EXAMPLES/Python/WIEGAND_CODE/wiegand.py
def callback(bits, value): print("bits={} value={}".format(bits, value)) todef callback(bits, value): print("bits={} value={}".format(bits, value)) print(int(bin(value)[3:27],2)) for remove CRC bits and convert to integer and print

Only first key 0009030510 correct read and print
bits=26 value=51615453 9030510
[u]other keys returns an incorrect value[/u]
0009487621 return 2198027
0009236067 return 1694918
0009328295 return 1879374

I tried to understand what the problem is, not work
translation into binary values, is evident that they are shifted

100010011100101101101110
100010011100101101101110
---------
0009487621=2198027
100100001100010100000101
   1000011000101000001011
---------
0009236067=1694918
100011001110111001100011
    110011101110011000110
---------
0009328295=1879374
100011100101011010100111
    111001010110101001110```

RPi2

Hi

is it compatible with RPi2?

Thanks... Béla

start() hangs

Code:

    import pigpio
    pigpio.start()
    pigpio.stop()

Result (only comes after Ctrl+C):

$ sudo python test.py 
^CTraceback (most recent call last):
  File "test.py", line 4, in <module>
    pigpio.start()
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 1547, in start
    _notify = _callback_thread()
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 346, in __init__
    self.handle = _pigpio_command(self.sock, _PI_CMD_NOIB, 0, 0)
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 316, in _pigpio_command
    x, y, z, res = struct.unpack('IIII', sock.recv(16))
KeyboardInterrupt

Sample time vs CPU utilisation

The documentation states the following figures:

The approximate CPU percentage used for each sample rate is:

sample  cpu
 rate    %

  1     25
  2     16
  4     11
  5     10
  8     15
 10     14

How were these numbers measured?
On my B+ board the sample rate of 10 us causes definitely a few percentages less utilization than 5 us.

Feasible Interrupt support?

Currently as far as I understand gpioSetAlertFunc() and gpioSetAlertFuncEx() use busy-waiting to implement: gpios are sampled every 5 us by default.
But with newer kernel, in RPi.GPIO and wiringPi there are interrupt support now. They also use threads, but the thread is waken up by the kernel when kernel detects an interrupt.
The problem is kernel<->userland content switch is costy on Linux.
So it is feasible to implement interrupt support in pigpio?

PWM set issue

Using a new install compile and load pigpiod -t 1
from python load library and associate local pi and issue
pi.set_PWM_range(6,500)
I assumed this would give me ~2ms pulse width increments, however measuring on a scope I get
pi.set_PWM_dutycycle(6,0)
actual pulse width 0
and 0 right up to set dutycycle 3 where I get a pulse width of 4.6us
this in itself is not an issue however -
Set Actual
4 4.7
5 9.7
6 9.7
7 9.7
8 14.69
9 14.69
10 19.68
11 19.68
12 19.68
13 24.68

Ignoring absolute values as errors in my scope measurements I would have expected to the pulse width to increment consistently.
Any ideas as to what may be going wrong ?

Allow only 0 to 255 in set_pwm

Setting a value of more than 255 or less than 0 to set_PWM_dutycycle makes no sense of course.

But when you do something like

i = 255
while i > 0:
    set_PWM_dutycycle(PIN, i)
    i -= 2

you will get the error pigpio.error: 'dutycycle not 0-range (default 255)'.
Maybe it would be a good idea to say: everything smaller than 0 means off, and everything larger than 255 means 100% on.
I modified set_PWM_dutycycle with

if dutycycle < 0:
    dutycycle = 0
if dutycycle > 255:
    dutycycle = 255

to do this for me.

1-wire doesn't work when using pigpiod

I'm having issues with pigpiod in combination with 1-wire.
When pigpiod is not running, the 1-wire sensor (DS18B20) can be read without any problems.

However, when I'm also reading measurements from a DHT22 -- using pigpiod and the DHTXXD executable -- I find that the 1-wire sensor file (w1_slave) occasionally disappears from /sys/bus/w1/devices/28*/. (DS18B20 id: 28-000006978d28)

Ultimately, this ends in a kernel "Oops" like this (sorry journalctl lines seem to have been truncated):

Apr 26 18:49:24 rbagain kernel: Unable to handle kernel NULL pointer dereference at virtual address 00000004
Apr 26 18:49:24 rbagain kernel: pgd = dd3e0000
Apr 26 18:49:24 rbagain kernel: [00000004] *pgd=1d2da831, *pte=00000000, *ppte=00000000
Apr 26 18:49:25 rbagain kernel: Internal error: Oops: 817 [#1] PREEMPT ARM
Apr 26 18:49:25 rbagain kernel: Modules linked in: cpufreq_stats nfsd nfs_acl rpcsec_gss_krb5 auth_rpcgss oid_registry nfsv4 dns_res
Apr 26 18:49:25 rbagain kernel: CPU: 0 PID: 841 Comm: python Not tainted 3.18.0-trunk-rpi #1 Debian 3.18.5-1~exp1+rpi19
Apr 26 18:49:25 rbagain kernel: task: dd003200 ti: dc71e000 task.ti: dc71e000
Apr 26 18:49:25 rbagain kernel: PC is at w1_slave_show+0x2d8/0x398 [w1_therm]
Apr 26 18:49:25 rbagain kernel: LR is at vsnprintf+0x294/0x414
Apr 26 18:49:25 rbagain kernel: pc : [<bf02336c>]    lr : [<c02c8544>]    psr: 80000013
                                sp : dc71fe08  ip : bf0235e0  fp : dc71fe54
Apr 26 18:49:25 rbagain kernel: r10: dc71fe27  r9 : 00000017  r8 : dc71fe27
Apr 26 18:49:25 rbagain kernel: r7 : dd3d4650  r6 : dd9e7000  r5 : 00000fe5  r4 : 00000000
Apr 26 18:49:25 rbagain kernel: r3 : 00000000  r2 : 1007ff7f  r1 : 464b0129  r0 : 0000000d
Apr 26 18:49:25 rbagain kernel: Flags: Nzcv  IRQs on  FIQs on  Mode SVC_32  ISA ARM  Segment user
Apr 26 18:49:25 rbagain kernel: Control: 00c5387d  Table: 1d3e0008  DAC: 00000015
Apr 26 18:49:25 rbagain kernel: Process python (pid: 841, stack limit = 0xdc71e1b0)
Apr 26 18:49:25 rbagain kernel: Stack: (0xdc71fe08 to 0xdc720000)
Apr 26 18:49:25 rbagain kernel: fe00:                   bf0235e8 dc71fe18 00000001 dc5a1c94 dc949040 297a41cc
Apr 26 18:49:25 rbagain kernel: fe20: 7f464b01 171007ff c011ed24 dc7dd600 bf023704 ddbe4200 00000fff 00001000
Apr 26 18:49:25 rbagain kernel: fe40: dd9e7000 c0575284 dc71fe6c dc71fe58 c0336928 bf0230a0 dc7dd600 dd3d4658
Apr 26 18:49:25 rbagain kernel: fe60: dc71fe9c dc71fe70 c01bba34 c0336908 c01bb998 00002000 dc71fec0 dc7dd600
Apr 26 18:49:25 rbagain kernel: fe80: dd029b40 00000001 00000001 dc71ff78 dc71feac dc71fea0 c01ba2dc c01bb9a4
Apr 26 18:49:25 rbagain kernel: fea0: dc71fefc dc71feb0 c016d970 c01ba2b4 dd029b48 00000000 dc7dd630 be993744
Apr 26 18:49:25 rbagain kernel: fec0: 00000000 00000000 dc71fefc dc71fed8 c0240000 ddbe4200 be993744 be993744
Apr 26 18:49:25 rbagain kernel: fee0: dc71ff78 00002000 00002000 be993744 dc71ff3c dc71ff00 c01badf0 c016d7b8
Apr 26 18:49:25 rbagain kernel: ff00: 571f9b6c 00000000 00000022 00000003 00000000 dd029b40 be993744 dc71e000
Apr 26 18:49:25 rbagain kernel: ff20: dc71ff78 00002000 dc71e000 be993744 dc71ff74 dc71ff40 c01498f4 c01bacd8
Apr 26 18:49:25 rbagain kernel: ff40: dc71ff5c dc71ff50 c0166930 00000000 00000000 dd029b40 dd029b40 00002000
Apr 26 18:49:25 rbagain kernel: ff60: dc71e000 be993744 dc71ffa4 dc71ff78 c0149a3c c0149864 00000000 00000000
Apr 26 18:49:25 rbagain kernel: ff80: 00000000 00002000 ffffffff 00000003 c000f884 00000000 00000000 dc71ffa8
Apr 26 18:49:25 rbagain kernel: ffa0: c000f640 c01499fc 00000000 00002000 00000004 be993744 00002000 00000000
Apr 26 18:49:25 rbagain kernel: ffc0: 00000000 00002000 ffffffff 00000003 020ca738 00002000 00002000 be993744
Apr 26 18:49:25 rbagain kernel: ffe0: 00000000 be9936a4 b6d9b234 b6df290c 60000010 00000004 00000000 00000000
Apr 26 18:49:25 rbagain kernel: [<bf02336c>] (w1_slave_show [w1_therm]) from [<c0336928>] (dev_attr_show+0x2c/0x58)
Apr 26 18:49:25 rbagain kernel: [<c0336928>] (dev_attr_show) from [<c01bba34>] (sysfs_kf_seq_show+0x9c/0x120)
Apr 26 18:49:25 rbagain kernel: [<c01bba34>] (sysfs_kf_seq_show) from [<c01ba2dc>] (kernfs_seq_show+0x34/0x38)
Apr 26 18:49:25 rbagain kernel: [<c01ba2dc>] (kernfs_seq_show) from [<c016d970>] (seq_read+0x1c4/0x4a0)
Apr 26 18:49:25 rbagain kernel: [<c016d970>] (seq_read) from [<c01badf0>] (kernfs_fop_read+0x124/0x16c)
Apr 26 18:49:25 rbagain kernel: [<c01badf0>] (kernfs_fop_read) from [<c01498f4>] (vfs_read+0x9c/0x198)
Apr 26 18:49:25 rbagain kernel: [<c01498f4>] (vfs_read) from [<c0149a3c>] (SyS_read+0x4c/0x98)
Apr 26 18:49:25 rbagain kernel: [<c0149a3c>] (SyS_read) from [<c000f640>] (ret_fast_syscall+0x0/0x30)
Apr 26 18:49:25 rbagain kernel: Code: eb4a9705 e5173004 e51b2031 e51b1035 (e5832004)
Apr 26 18:49:25 rbagain kernel: ---[ end trace 028330aecbc655fa ]---

Some basic system info:

$ uname -a
Linux rbagain 3.18.0-trunk-rpi #1 PREEMPT Debian 3.18.5-1~exp1+rpi19 (2015-08-08) armv6l GNU/Linux
$ cat /etc/modules
bcm2708-rng
w1-therm
w1-gpio

source: http://abyz.co.uk/rpi/pigpio/code/DHTXXD.zip

DHTXXD.h : 2015-11-15
DHTXXD.c : 2016-02-16
$ pigpiod -v
51

timestamping with CLOCK_REALTIME

Hello everyone,

First of all I would like to say thank you for this great piece of soft.

In my aplication I need to get precise UTC timestamp of gpio activation. I learnt that pigpio is capable of timestamping gpio changes with precision of microseconds but using system ticks but the traslation to UTC is not so obvious if you consider latencies, clock jitters...

I know that normal system "wall clock" deviate to much to consider for a precise timestamping. To avoid that I run a NTP Stratum 1 using a GPS and PPS that get system clock between +/-10 microseconds of UTC.

Could be posible to use CLOCK_REALTIME in order to obtain a UTC timestamp with pigpio?

Thank in advance

pigpiod shutdown problem (kernel 4.1.12+)

root@raspberrypi ~ # uname -a
Linux raspberrypi 4.1.12+ #824 PREEMPT Wed Oct 28 16:39:49 GMT 2015 armv6l GNU/Linux

pigpiod current version, recompiled and reinstall
make uninstall
make clean
make install

shutdown -h now
on screen this error _and computer restarted (not shutdown)_
Shutdown error

pigpio.py: close and atexit not the best method

The current registration of close as an atexit callback isn't the best way to clean up - resources
will only be freed at program exit (which is almost pointless).

I'm seeing a problem with a long-running python script
with many pigpio connections - it's running out of resources to create threads.

For now, my fix is to explicitly call close.

However, the better solution would be to use a del destructor to call close once
the reference to the pigpio class is out of scope.

DHT11 Example code

I received a message as follows.

I've pulled up the python script dht11.py in the EXAMPLES directory and ran it with a DHT11 attached to the gpio as described in the online manuals. After reformatting the Print statement to list the Temp and Rel Humid on one line, what I get is:

================================ RESTART ================================

T: 0 C, RH: 0 %
T: 0 C, RH: 0 %
T: 0 C, RH: 0 %
T: 0 C, RH: 0 %

Exception in thread Thread-1:
Traceback (most recent call last):
File "/usr/lib/python2.7/threading.py", line 552, in __bootstrap_inner self.run()
File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 868, in run cb.func(cb.gpio, newLevel,
tick)
File "/home/pi/pigpio/EXAMPLES/Python/DHT11_SENSOR/dht11.py", line 69, in
either_edge_callback handler(tick, diff)
File "/home/pi/pigpio/EXAMPLES/Python/DHT11_SENSOR/dht11.py", line 91, in _edge_RISE
raise
TypeError: exceptions must be old-style classes or derived from BaseException, not NoneType

T: 25 C, RH: 36 %
T: 25 C, RH: 36 %
T: 25 C, RH: 36 %
T: 25 C, RH: 36 %

=== I hit CTRL-C to kill it ===

So, the code returns 0's for Temperature and Humidity until it hits some exception and then it starts getting and listing the reasonable (actual?) values. Any idea what is going wrong at the start? Sometimes it gives 0's for quite awhile before it hits the exception and starts giving real values. Other times it will stay at T=0, but return low humidity values like 1% or 5% and continues on without hitting the exception, but this is much less common.

I will have a look at the problem but can't commit to a time-scale.

Function get_PWM_frequency() return 800Hz when hardware PWM freq is set to zero.

Hello,

I found that get_PWM_frequency() reports 800Hz in stead of 0Hz when hardware_PWM freq is set to zero. PWM really stop. Here I paste sample code showing the issue:

#!/usr/bin/python

import pigpio
if __name__ == '__main__':
    pi=pigpio.pi("cronostamper")
    pi.set_mode(13, pigpio.OUTPUT)
    for f in [142,2323,0,4320,1,0]:
        pi.hardware_PWM(13,f,500000)
        print "Hardware PWM/get_PWM_frequency()",f,"/",pi.get_PWM_frequency(13)

Executing this code shows:

Hardware PWM/get_PWM_frequency() 142 / 142
Hardware PWM/get_PWM_frequency() 2323 / 2323
Hardware PWM/get_PWM_frequency() 0 / 800
Hardware PWM/get_PWM_frequency() 4320 / 4320
Hardware PWM/get_PWM_frequency() 1 / 1
Hardware PWM/get_PWM_frequency() 0 / 800

Nacho

Multiple programs besides the daemon run

Hi,

I have a question regarding a parallel usage of the daemon and other non-daemon programs at the same time. I use one program which writes via PWM through pigpiod to a pin and I have other programs which work on different pins at the same time. When the daemon runs, I get

2016-05-17 02:54:22 initInitialise: Can't lock /var/run/pigpio.pid

Is it save to just write to a different pid file or are there any serious problems when doing this in parallel?

Thanks!

Writing a Python module with pigpio

Hi!
I have a function which can fade some LEDs, it works without a problem. When I put the function into another file, import it into my main file and call it from there I get the following error:

Exception in thread Thread-1:
Traceback (most recent call last):
  File "/usr/lib/python2.7/threading.py", line 810, in __bootstrap_inner
    self.run()
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 923, in run
    lastLevel = _pigpio_command(self.control,  _PI_CMD_BR1, 0, 0)
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 835, in _pigpio_command
    dummy, res = struct.unpack('12sI', sl.s.recv(16))
AttributeError: 'NoneType' object has no attribute 'recv'

Same thing when using an event like a button press from the build in GPIO Python library.

gpioTerminate and interrupt callbacks

If gpioTerminate is called when interrupt callbacks are active the system is left in an inconsistent state. In order to get the system back into a consistent state a reboot is required.

This can be seen with the following program:

#include <unistd.h>
#include <stdio.h>
#include <pigpio.h>

#define GPIO 4

void isr(int gpio, int level, uint32_t tick) {
  printf("isr - gpio: %d, level: %d\n", gpio, level);
}

int main(int argc, char *argv[]) {
  int version;

  if ((version = gpioInitialise()) < 0) {
    return -1;
  }

  printf("version: %d\n", version);

  if (gpioSetISRFunc(GPIO, EITHER_EDGE, 200, isr) != 0) {
    return -1;
  }

  sleep(1);

  gpioTerminate();
}

The first run of this program outputs the following:

version: 39
isr - gpio: 4, level: 2
isr - gpio: 4, level: 2
isr - gpio: 4, level: 2
isr - gpio: 4, level: 2
2015-10-31 07:47:46 sigHandler: Unhandled signal 11, terminating

The second run outputs the following:

2015-10-31 07:47:50 initMboxBlock: init mbox zaps failed

The first run of the program appears to leave the system in an inconsistent state that prevents the program from running successfully a second time.

If the test program is modified to disable the interrupt before calling gpioTerminate everything functions correctly and the program can be run mutiple times successfully.

#include <unistd.h>
#include <stdio.h>
#include <pigpio.h>

#define GPIO 4

void isr(int gpio, int level, uint32_t tick) {
  printf("isr - gpio: %d, level: %d\n", gpio, level);
}

int main(int argc, char *argv[]) {
  int version;

  if ((version = gpioInitialise()) < 0) {
    return -1;
  }

  printf("version: %d\n", version);

  if (gpioSetISRFunc(GPIO, EITHER_EDGE, 200, isr) != 0) {
    return -1;
  }

  sleep(1);

  if (gpioSetISRFunc(GPIO, EITHER_EDGE, 0, NULL) != 0) {
    return -1;
  }

  gpioTerminate();
}

Would it not be better if gpioTerminate disabled interrupts and unexported the appropriate gpios instead of requiring gpioSetISRFunc to be called to perform the task?

Ease cross-compilation

Currently, it's quite difficult to build pigpio using a cross compiler. I actually have to change every single command. Additionally, the install target does not allow to set a prefix path for a custom install location.

Could this please be fixed?

Makefile root priviledges

Would it be possible to remove sudo calls from Makefile and let people execute the script as sudo? This would solve issue eg. in Minibian where the sudo is not present.

timeout when setting a callback

Hi Joan,

I hope you can help with this issue.

On raspberry pi 2 I have installed pigpio and python binding and I am trying to setup an input callback function. In few seconds after setting the callback I get the following error:

Oct 21 01:02:30 pi-face userspaceServices[6329]: 2015-10-21 01:02:30,846 haiot INFO init:setup_in_ports Set pincode=11 type=pi-stdgpio index=11 as input
Oct 21 01:02:40 pi-face userspaceServices[6329]: Traceback (most recent call last):
Oct 21 01:02:40 pi-face userspaceServices[6329]: File "/usr/lib/python2.7/threading.py", line 810, in __bootstrap_inner
Oct 21 01:02:40 pi-face userspaceServices[6329]: self.run()
Oct 21 01:02:40 pi-face userspaceServices[6329]: File "/home/haiot/PYC/venv/local/lib/python2.7/site-packages/pigpio.py", line 908, in run
Oct 21 01:02:40 pi-face userspaceServices[6329]: buf = self.sl.s.recv(MSG_SIZ)
Oct 21 01:02:40 pi-face userspaceServices[6329]: timeout: timed out

My init code is as follows:
........
import pigpio
__callback = []
__pi = pigpio.pi()
__pi.set_mode(11, pigpio.INPUT)
__callback.append(__pi.callback(user_gpio=11,
edge=pigpio.EITHER_EDGE, func=input_event))
...

def input_event(gpio, level, tick):
Log.logger.info("Received pigpio input gpio={} level={} tick={}".format(gpio, level, tick))
.........
Command pigs MG 11 works fine:
root@pi-face:~# pigs MG 10
4

A question about callbacks and ticks

The gpioSetAlertFunc provided by the pigpio C interface can be used to register a callback function to detect gpio state changes. Has the percision and accuracy of the tick value passed to the callback function improved in a recent version of pigpio? The tick values I'm seeing with V45 look better than those that I was seeing with V42.

Hardware revision on raspberry pi 2

On the raspberry pi 2, the hwver command returns 10620993

pi@raspberrypi ~/tmp $ pigs hwver
10620993

I get the same result when using the socket interface (directly or with the python client lib).

When I look at /proc/cpuinfo I find 1041, which match the information found here

pi@raspberrypi ~/tmp $ cat /proc/cpuinfo 
[...]
Hardware        : BCM2709
Revision        : a21041
Serial          : 00000000030b1d4f

Really not a big deal, I just wanted to let you know.

DHT22.py sample code returns: AttributeError: 'NoneType' object has no attribute 'send'

I'm trying to use your DHT22.py sample code to return a single temperature and humidity reading from an AM2302 sensor. When I modified your code to only return one reading and then exit I received the following errors:

52.9 24.1 0.18 0 0 0 0
Error in atexit._run_exitfuncs:
Traceback (most recent call last):
  File "/usr/lib/python2.7/atexit.py", line 24, in _run_exitfuncs
    func(*targs, **kargs)
  File "./get_temp_DHT22.py", line 239, in cancel
    self.pi.set_watchdog(self.gpio, 0)
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 1410, in set_watchdog
    self.sl, _PI_CMD_WDOG, user_gpio, int(wdog_timeout)))
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 806, in _pigpio_command
    sl.s.send(struct.pack('IIII', cmd, p1, p2, 0))
AttributeError: 'NoneType' object has no attribute 'send'
Error in sys.exitfunc:
Traceback (most recent call last):
  File "/usr/lib/python2.7/atexit.py", line 24, in _run_exitfuncs
    func(*targs, **kargs)
  File "./get_temp_DHT22.py", line 239, in cancel
    self.pi.set_watchdog(self.gpio, 0)
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 1410, in set_watchdog
    self.sl, _PI_CMD_WDOG, user_gpio, int(wdog_timeout)))
  File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 806, in _pigpio_command
    sl.s.send(struct.pack('IIII', cmd, p1, p2, 0))
AttributeError: 'NoneType' object has no attribute 'send'

Here is my main which only makes one sensor reading.

if __name__ == "__main__":
   import time
   import pigpio

   pi = pigpio.pi()

#  s = DHT22.sensor(pi, 22, LED=16, power=8)
   s = sensor(pi, 4 )   # My AM2302 is on GPIO Pin #4

   s.trigger()
   time.sleep(0.2)

   print("{} {} {:3.2f} {} {} {} {}".format(
         s.humidity(), s.temperature(), s.staleness(),
         s.bad_checksum(), s.short_message(), s.missing_message(),
         s.sensor_resets()))

   s.cancel()
   pi.stop()

I made the following change to the cancel method of your DHT22 sensor class. I added an if to ensure that sl.s wasn't None before call set_watchdog. This appears to work, but I'm sure that this violates all the principles of object-oriented programming.

   def cancel(self):
      """Cancel the DHT22 sensor."""

      if self.pi.sl.s is not None:
         self.pi.set_watchdog(self.gpio, 0)

      if self.cb != None:
         self.cb.cancel()
         self.cb = None

Is there a better way to do this?

Also, what actions should I take to ensure that I got a valid reading?

cgi can't connect to pigpio

I've tried to run a cgi example from pigpio python CGI abyz.co.uk site and it doesn't work. When i open site http://rpiAdress/pigpio_cgi.py it show error on top of the page:
"Can't connect to pigpio on soft(8889) Did you start the pigpio daemon? E.g. sudo pigpiod Did you specify the correct Pi host/port in the environment variables PIGPIO_ADDR/PIGPIO_PORT? E.g. export PIGPIO_ADDR=soft, export PIGPIO_PORT=8888 Did you specify the correct Pi host/port in the pigpio.pi() function? E.g. pigpio.pi('soft', 8888))"
I run sudo pigpiod -p 8889 before.(port 8888 is also not working)
pigpiod is working well becouse I have an application on Windows which can connect and use pigpio over network and is work properly.
Whan I need to do? (also node.js can't connect to pigpio)

Notifications with incorrect sequence numbers

The effect seen here may be an edge case, or I may be doing something incorrectly, or I may be expecting too much.

The following program starts hardware PWM on GPIO18 at a frequency of 100KHz with a 50% duty cycle. It then activates notifications on GPIO18. This means about 200,000 notifications per second. Every 1,000,000 notifications the program prints the number of notifications so far. If the seqno for a notification is not the expected value an error message is printed.

#include <fcntl.h>
#include <stdio.h>
#include <pigpio.h>

#define LED 18

int main() {
  int version;
  int handle;
  char pipePath[32];
  int fd;
  int bytes;
  int notificationCount = 0;
  gpioReport_t r;
  uint16_t lastSeqno = 0xffff;
  uint32_t lastTick;

  gpioCfgClock(1, 1, 1);

  if ((version = gpioInitialise()) < 0) {
    printf("gpioInitialise error\n");
    return -1;
  }

  printf("version: %d\n", version);

  if (gpioHardwarePWM(LED, 100000, 500000) < 0) {
    printf("gpioHardwarePWM error\n");
    return -1;
  }

  if ((handle = gpioNotifyOpen()) < 0) {
    printf("gpioNotifyOpen error\n");
    return -1;
  }

  if (gpioNotifyBegin(handle, (1 << LED)) < 0) {
    printf("gpioNotifyBegin error\n");
    return -1;
  }

  sprintf(pipePath, "/dev/pigpio%d", handle);

  if ((fd = open(pipePath, O_RDONLY)) < 0) {
    printf("open error\n");
    return -1;
  }

  for (;;) {
    bytes = read(fd, &r, 12);
    if (bytes != 12) {
      printf("read error\n");
      return -1;
    }

    notificationCount++;
    if (notificationCount % 1000000 == 0) {
      printf("%d\n", notificationCount);
    }

    if (((uint16_t) (lastSeqno + 1)) != r.seqno) {
      printf("  sequence error - lastSeqno: %d, seqno: %d\n", lastSeqno, r.seqno);
      printf("    %d\n", notificationCount);
    }

    lastSeqno = r.seqno;
    lastTick = r.tick;
  }

  gpioTerminate();

  return 0;
}

If the program is run without any additional load everything looks fine and the output will be something like this:

version: 40
1000000
2000000
3000000
4000000
5000000
6000000
7000000
8000000
9000000
10000000
11000000
12000000
13000000
14000000
15000000
16000000
17000000
18000000
19000000
20000000
...

However, if there is additional load on the system, the output can look like this:

version: 40
1000000
2000000
  sequence error - lastSeqno: 28427, seqno: 28583
    2780941
  sequence error - lastSeqno: 31399, seqno: 32082
    2783758
  sequence error - lastSeqno: 32199, seqno: 33000
    2783876
  sequence error - lastSeqno: 33340, seqno: 33800
    2784217
  sequence error - lastSeqno: 34140, seqno: 34452
    2784558
  sequence error - lastSeqno: 34792, seqno: 35701
    2784899
  sequence error - lastSeqno: 38414, seqno: 39273
    2787613
  sequence error - lastSeqno: 39613, seqno: 40075
    2787954
  sequence error - lastSeqno: 40415, seqno: 40873
    2788295
  sequence error - lastSeqno: 41213, seqno: 42072
    2788636
  sequence error - lastSeqno: 42412, seqno: 42470
    2788977
  sequence error - lastSeqno: 42870, seqno: 43212
    2789378
  sequence error - lastSeqno: 44811, seqno: 44870
    2790978
  sequence error - lastSeqno: 45611, seqno: 46071
    2791720
  sequence error - lastSeqno: 46411, seqno: 46872
    2792061
  sequence error - lastSeqno: 47212, seqno: 47669
    2792402
  sequence error - lastSeqno: 48009, seqno: 48471
    2792743
  sequence error - lastSeqno: 48811, seqno: 49671
    2793084
  sequence error - lastSeqno: 50011, seqno: 50071
    2793425
  sequence error - lastSeqno: 50411, seqno: 50485
    2793766
  sequence error - lastSeqno: 51670, seqno: 52012
    2794952
  sequence error - lastSeqno: 52069, seqno: 52411
    2795010
  sequence error - lastSeqno: 52471, seqno: 52813
    2795071
  sequence error - lastSeqno: 52871, seqno: 53213
    2795130
  sequence error - lastSeqno: 53609, seqno: 54470
    2795527
  sequence error - lastSeqno: 55211, seqno: 55672
    2796269
  sequence error - lastSeqno: 56012, seqno: 56473
    2796610
  sequence error - lastSeqno: 56813, seqno: 56872
    2796951
  sequence error - lastSeqno: 57212, seqno: 57673
    2797292
  sequence error - lastSeqno: 58013, seqno: 58472
    2797633
  sequence error - lastSeqno: 58812, seqno: 58872
    2797974
  sequence error - lastSeqno: 59212, seqno: 59671
    2798315
  sequence error - lastSeqno: 60833, seqno: 61271
    2799478
  sequence error - lastSeqno: 61611, seqno: 62070
    2799819
  sequence error - lastSeqno: 62410, seqno: 62471
    2800160
  sequence error - lastSeqno: 63212, seqno: 63672
    2800902
  sequence error - lastSeqno: 64012, seqno: 64470
    2801243
  sequence error - lastSeqno: 64810, seqno: 64870
    2801584
  sequence error - lastSeqno: 65210, seqno: 134
    2801925
  sequence error - lastSeqno: 474, seqno: 602
    2802266
  sequence error - lastSeqno: 1274, seqno: 1735
    2802939
  sequence error - lastSeqno: 2875, seqno: 3337
    2804080
  sequence error - lastSeqno: 3677, seqno: 3773
    2804421
  sequence error - lastSeqno: 4113, seqno: 4536
    2804762
  sequence error - lastSeqno: 5290, seqno: 5735
    2805517
  sequence error - lastSeqno: 6075, seqno: 6135
    2805858
  sequence error - lastSeqno: 6475, seqno: 6934
    2806199
  sequence error - lastSeqno: 7274, seqno: 7336
    2806540
  sequence error - lastSeqno: 7676, seqno: 8135
    2806881
  sequence error - lastSeqno: 8475, seqno: 8536
    2807222
  sequence error - lastSeqno: 8876, seqno: 9336
    2807563
  sequence error - lastSeqno: 10875, seqno: 11381
    2809103
  sequence error - lastSeqno: 11721, seqno: 12136
    2809444
  sequence error - lastSeqno: 12902, seqno: 12935
    2810211
  sequence error - lastSeqno: 13275, seqno: 13737
    2810552
  sequence error - lastSeqno: 14077, seqno: 14133
    2810893
  sequence error - lastSeqno: 14473, seqno: 14936
    2811234
  sequence error - lastSeqno: 15276, seqno: 15737
    2811575
  sequence error - lastSeqno: 16077, seqno: 16136
    2811916
  sequence error - lastSeqno: 16476, seqno: 16934
    2812257
  sequence error - lastSeqno: 17676, seqno: 17733
    2813000
  sequence error - lastSeqno: 18073, seqno: 18136
    2813341
  sequence error - lastSeqno: 18476, seqno: 18536
    2813682
  sequence error - lastSeqno: 18876, seqno: 18935
    2814023
  sequence error - lastSeqno: 19275, seqno: 19736
    2814364
  sequence error - lastSeqno: 20519, seqno: 20937
    2815148
  sequence error - lastSeqno: 21377, seqno: 21719
    2815589
  sequence error - lastSeqno: 22074, seqno: 22556
    2815945
3000000
4000000

The sequence numbers are often off by a few hundred here. The additional load in this case was an scp command which copied a large file from another Linux machine to the Pi.

Setting the PWM frequency to 200KHz will result in similar sequence number issues without any additional load on the system.

Is this to be expected or am I doing something incorrectly?

Hardware PWM on two channels causes initialisation glitch

Hi,
I need to drive two steppers using independent PWM hardware with variable frequency. I use gpio 12 and 13 that is supposed to have different channels but when I change the frequency of one of them the other is disturbed, piscope shows spikes. When I stop changing, each channels get its right frequency. The problem is when setting freq with hardware_PWM function. This is the code:

#!/usr/bin/python
import pigpio
import time
if __name__ == '__main__':
    pi=pigpio.pi("cronostamper")
    pi.set_mode(12, pigpio.OUTPUT)
    pi.set_mode(13, pigpio.OUTPUT)
    pi.hardware_PWM(12,10,500000)
    for i in range(100):
        t1 = pi.get_current_tick()
        pi.hardware_PWM(13,i*1,500000)
        t2 = pi.get_current_tick()
        print pigpio.tickDiff(t1,t2)
        time.sleep(0.050)

Any advice are wellcome
Cheers,

pigpiod does not repsond to python test app

Hi Joan,
I installed the latest pigpio (via cloned repo) on my RPi with Raspbian linux and Python 3.2. After installation

make
make install
python3.2 setup.py install

I can successfully run (with all tests passing):

sudo ./x_pigpio

When I start the demon (sudo pigpiod) and try to open a socket in Python, I get a timeout (after some waiting):

>>> s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
>>> s.connect(('localhost', 8888))
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
socket.error: [Errno 110] Connection timed out

Running pigpio.start() returns with the standard error message (and hints) after the timeout. I have no idea why this happens and pigpiod is not answering.
I ensured that the port 8888 is available before running pigpiod and that it is listened at after starting pigpiod.

Best
Jonas

Question on the socket protocol

I have a question on the use of notifications with the socket protocol. Notification support is buggy in my asyncio client implementation and I'm not sure if I understand correctly the the way it is supposed to be used.

This what I infer when reading the python client code : when using notification with sockets, one must use two socket a and b:

  • the socket a is used to send the request for notifications and get an handle. Once the notification has been started, this socket is only used to read notifications and should not be used for anything else.
  • the socket b is used to send start and pause notification commands (and any other command), the same handle can be used to start several notification on different gpio.

Is that correct ?

3-wire spi doesn't work

I open my spi-dev0 as follow(10kbps,set the 'W' flag as document says):
spi = pi.spi_open(0,10000,0x200)
and then i write the data with this:
pi.spi_write(spi,[0x01,0x02,0x03,0x04])
However,no output on MISO or MOSI.Where is wrong?Is 3-wire spi supported?

make -f MakeRemote needs 3 invokations to complete?

Reading the README pointed out the ability to compile the remote capabilities (and to generate the man pages locally - which is useful when sshing into a headless RPi for creation/compiling code).

However the compilation took three attempts before completing - is this to be expected for a fresh install?

Preliminary step:

stephen@Ripley:/src/pigpio$ make -f MakeRemote clean
rm -f *.o *.i *.s *
libpigpiod_if.so libpigpiod_if2.so pigs x_pigpiod_if x_pigpiod_if2

1st try:

stephen@Ripley:~/src/pigpio$ make -f MakeRemote
gcc -O3 -Wall -pthread -fpic -c -o pigpiod_if.o pigpiod_if.c
gcc -O3 -Wall -pthread -fpic -c -o command.o command.c
gcc -O3 -Wall -pthread -fpic -c -o pigpiod_if2.o pigpiod_if2.c
gcc -O3 -Wall -pthread -c -o pigs.o pigs.c
gcc -O3 -Wall -pthread -c -o x_pigpiod_if.o x_pigpiod_if.c
gcc -O3 -Wall -pthread -c -o x_pigpiod_if2.o x_pigpiod_if2.c
gcc -o x_pigpiod_if x_pigpiod_if.o -L. -lpigpiod_if -pthread -lrt
/usr/bin/ld: cannot find -lpigpiod_if
collect2: error: ld returned 1 exit status
make: *** [x_pigpiod_if] Error 1
make: *** Waiting for unfinished jobs....

2nd try:

stephen@Ripley:~/src/pigpio$ make -f MakeRemote
gcc -shared -o libpigpiod_if.so pigpiod_if.o command.o
gcc -shared -o libpigpiod_if2.so pigpiod_if2.o command.o
gcc -O3 -Wall -pthread -fpic -o pigs pigs.c command.c
gcc -o x_pigpiod_if x_pigpiod_if.o -L. -lpigpiod_if -pthread -lrt
gcc -o x_pigpiod_if2 x_pigpiod_if2.o -L. -lpigpiod_if2 -pthread -lrt
/usr/bin/ld: cannot find -lpigpiod_if
./libpigpiod_if2.so: file not recognized: File truncated
collect2: error: ld returned 1 exit status
make: *** [x_pigpiod_if] Error 1
make: *** Waiting for unfinished jobs....
collect2: error: ld returned 1 exit status
make: *** [x_pigpiod_if2] Error 1
strip --strip-unneeded libpigpiod_if2.so
strip --strip-unneeded libpigpiod_if.so
size libpigpiod_if2.so
size libpigpiod_if.so
text data bss dec hex filename
69539 6624 49408 125571 1ea83 libpigpiod_if.so
text data bss dec hex filename
56875 6592 2592 66059 1020b libpigpiod_if2.so

3rd and successfully completed try:

stephen@Ripley:/src/pigpio$ make -f MakeRemote
gcc -o x_pigpiod_if x_pigpiod_if.o -L. -lpigpiod_if -pthread -lrt
gcc -o x_pigpiod_if2 x_pigpiod_if2.o -L. -lpigpiod_if2 -pthread -lrt
stephen@Ripley:
/src/pigpio$ make -f MakeRemote
make: Nothing to be done for `all'.

It isn't a major issue but it might be worth pointing out in the top-level README...

Also for the installation step:

stephen@Ripley:~/src/pigpio$ sudo make -f MakeRemote install
[sudo] password for stephen:
install -m 0755 -d /usr/local/include
install -m 0644 pigpio.h /usr/local/include
install -m 0644 pigpiod_if.h /usr/local/include
install -m 0644 pigpiod_if2.h /usr/local/include
install -m 0755 -d /usr/local/lib
install -m 0644 libpigpiod_if.so /usr/local/lib
install -m 0644 libpigpiod_if2.so /usr/local/lib
install -m 0755 -d /usr/local/bin
install -m 0755 pigs /usr/local/bin
python2 setup.py install
running install
running build
running build_py
creating build
creating build/lib.linux-x86_64-2.7
copying pigpio.py -> build/lib.linux-x86_64-2.7
running install_lib
copying build/lib.linux-x86_64-2.7/pigpio.py -> /usr/local/lib/python2.7/dist-packages
byte-compiling /usr/local/lib/python2.7/dist-packages/pigpio.py to pigpio.pyc
running install_egg_info
Writing /usr/local/lib/python2.7/dist-packages/pigpio-1.27.egg-info
python3 setup.py install
make: python3: Command not found
make: *** [install] Error 127

I only have python 2.x installed, so the installation bailing out when it can't find python3 is not surprising - I dunno whether it is worth checking to see which version(s) are around before trying to install for them, obviously your work is focused on the RPi end of things and the effort to have support for the extra remote features on lots of different host types is going to hit the diminishing returns curve fairly quickly!

Raspberry version check

I have recently updated my pigpio library and now it says I can't change certain pins. I tracked it down to a wrong value report (or comparison) of the hardware revision. The python function get_hardware_revision() returns 19 and from pigpio's standpoint that should be a raspberry pi B, but I got a B+.
I use pigpio V49, pigpio.VERSION reports 1.30.

Cant initialise

Calling gpioInitialise from c results in following error:

initAllocDMAMem: mbox open failed(No such device or address)

I am using the latest version from 30-08-2015

Access to gpio pin 35 (power led on type3 boards)

I know pigpiod allows by default changing state of the activity led (gpio47). Would it be possible to also allow default access to the power led of a type3 board? This is gpio35

Btw. great piece of software! :-)

DHT11 pigpio Anomalies with Jessie Environment

The code contribution at 523fe86 by srounet does not work under Python 3 under Jessie on RPi for a DHT11 sensor. After the very nominal syntax change for the iter definition, the module runs, throws an exception after the first iteration and continues to report constant values for temperature and relative humidity despite changes in the ambient conditions. The numbers themselves are spurious because they vary for each separate invocation of the module. Since I have the sensor working with the wiringPi library without any modifications to the breadboard, I will use joan2937's suggestion to use the new library at http://abyz.co.uk/rpi/pigpio/examples.html#pdif2_DHTXXD for further experiments (including DHT22) but I thought I would pass along my note in the event others seeking a Python 3 solution (for whatever reason) spin futile cycles to make this particular code work. I did not try the DHT22 sensor with the original code.

Of course, I will be willing to test any forthcoming revisions to the code. I understand the caveats in using these types of sensors under RPi's OS since I have an Arduino UNO sending back correct data to its RPi host via the Python pyserial module on the RPi. The only reason I became partial to Python was owing to the ease in using SQLite and MySQL interfaces through Python for further extensions.

Thanks for your guidance. Rdgs.

Is it possible to support NEO-PIXELS now?

Having spotted the rpi-ws821x library mentioned on the Adafruit site I was wondering whether it's use of the Hardware PWM could be incorporated (Licence renegotiation permitting) into pigpio?

I have a couple of those sort of strips and wanted to incorporate them into my wicked-plans 😏 but I was aware that in the past the timing was too tight to do on any RPi - I was contemplating designing a PIC or other micro-controller buffer to accept a 2-wire serial output that RPis (and pigpio) should easily(?) be able to do and then squirt out the tightly timed 1-wire serial equivalent that the WS8211B IC (and the WS8212B LED module incorporating it) that cheaper LED strips have - then I realised that I might have pixel data storage issues unless I got a bit inventive. So if this is something that could be done in the light of developments in PWM coding it might be quite useful.

Failing that - if I have to reserve the PWM stuff for this other library - just how crippled will pigpio be without that facility?

pigpio error

I have started the pigpio daemon by sudo pigpiod
I am trying to interface a sensor to the pi via i2c
I am getting the following error:

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
Can't connect to pigpio on localhost(8888)

Did you start the pigpio daemon? E.g. sudo pigpiod

I am getting the following error when I am trying to use pigpio for i2c.
I have started the pigpio daemon by sudo pigpiod

Did you specify the correct Pi host/port in the environment
variables PIGPIO_ADDR/PIGPIO_PORT?
E.g. export PIGPIO_ADDR=soft, export PIGPIO_PORT=8888

Did you specify the correct Pi host/port in the
pigpio.pi() function? E.g. pigpio.pi('soft', 8888))
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
Traceback (most recent call last):
File "ina219_02_23_2016_pigpio.py", line 23, in
handle_ina_219 = pi.i2c_open(1, address_ina_219)
File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 2221, in i2c_open
self.sl, _PI_CMD_I2CO, i2c_bus, i2c_address, 4, extents))
File "/usr/local/lib/python2.7/dist-packages/pigpio.py", line 857, in _pigpio_command_ext
sl.s.sendall(ext)
AttributeError: 'NoneType' object has no attribute 'sendall'

Notification structure

Hi,
thanks for the nice lib!

Could you please clarify a thing or two for me!?
As given here I try to read /dev/pigpioX after subscribing for notifications but get _strange results_.

First I subscribe...

$ pigs no
0
$ pigs nb 0 240 // this should be (1<<4) | (1<<5) | (1<<6) | (1<<7)

Then I monitor /dev/pigpioX with Node.js this is my code:

var fs = require('fs'); // file system
var rstream = fs.createReadStream('/dev/pigpio0');
var binary = require('binary');

binary.stream(rstream)
    .loop(function (end, vars) {
        this
            .word16lu('seqno')
            .word16lu('flags')
            .word32lu('tick')
            .word32lu('level')
            .tap(function (vars_) {
                console.log(vars_);
            });
    });

It is plain simple code. What it does is:

  • Opens /dev/pigpioX for reading
  • Starts reading present data or waits for data
  • If data is present it loops in "frames" of 12 bytes as expected and assigns to the variables.
  • In the loop it dumps to stdout the vars (structure)

What I get is:

...
{ seqno: 30, flags: 0, tick: 3808029467, level: 2952839535 }
{ seqno: 31, flags: 0, tick: 3812660689, level: 2952839551 }
...

_Questions:_

  1. Why is flags 0? It looks that seqno is valid. I also compared tick with pigs T output. They are ~ equal.
    1.1 Why is level such int? Should it not be 0/1?
  2. Could you please confirm that the structure given is valid? 12 bytes 2+2+4+4?
  3. What is written exactly to /dev/pigpioX? Is it a sequence of notification structures? Is there some bytes for delimiter?
  4. I note that occasionally some events/new data occurs without me changing the gpios, why? This means something else is happening meanwhile?

Thanks in advance for any answers!

State changes not being detected with notifications

While testing the pigpio Node.js module I noticed that state changes don't always appear to be detected by the notification mechanisms provided by the pigpio C library. Similar issues can be seen when the pigpio C library is used directly, i.e., without the Node.js module.

Here is how the test was performed with the pigpio C library.

The following program was run on an ATmega328P clocked at 8 Mhz. The program generates generates 50000 pulses or 100000 state changes on PB1 of the ATmega. The pulses are approximately 8 microseconds wide with a 50% duty cycle. After generating the pulses, the program waits 5 seconds before repeating the same thing again.

/*
avr-gcc -Wall -c -g -Os -mmcu=atmega328p -DF_CPU=8000000UL pulse.c
avr-gcc -g -mmcu=atmega328p -o pulse.elf pulse.o
avr-objcopy -j .text -j .data -O ihex pulse.elf pulse.hex
sudo avrdude -c dragon_isp -P usb -p m328p -e -U flash:w:pulse.hex
*/

#include <avr/io.h>
#include <avr/power.h>
#include <util/delay.h>

#define LED PB0
#define LED_DDR DDRB
#define LED_PORT PORTB

#define PULSE PB1
#define PULSE_DDR DDRB
#define PULSE_PORT PORTB

#define DELAYTIME 4

#define setBit(sfr, bit) (_SFR_BYTE(sfr) |= (1 << bit))
#define clearBit(sfr, bit) (_SFR_BYTE(sfr) &= ~(1 << bit))
#define toggleBit(sfr, bit) (_SFR_BYTE(sfr) ^= (1 << bit))

int main(void) {
  uint32_t i;

  clock_prescale_set(clock_div_1); // 8Mhz clock

  setBit(LED_DDR, LED); // configure LED pin as an output
  setBit(PULSE_DDR, PULSE); // configure PULSE pin as an output

  while (1) {
    setBit(LED_PORT, LED); // LED on

    for (i = 0; i != 50000; ++i) {
      setBit(PULSE_PORT, PULSE); // PULSE high
      _delay_us(DELAYTIME);

      clearBit(PULSE_PORT, PULSE); // PULSE low
      _delay_us(DELAYTIME);
    }

    clearBit(LED_PORT, LED); // LED off

    _delay_ms(5000);
  }

  return (0);
}

PB1 on the ATmega328P is connected to GPIO18 on a Raspberry Pi 3. The following program is run on the Pi. It simply counts the number of state changes on GPIO18 and prints the number of state changes detected once per second.

// gcc -o pulsein pulsein.c -lpigpio -lpthread -lrt

#include <fcntl.h>
#include <stdio.h>
#include <pigpio.h>

#define PULSE_GPIO 18
#define BUF_SIZE 1000

static uint32_t notificationCount = 0;

void timerFunc(void) {
  printf("%u\n", notificationCount);
}

int main() {
  int version;
  int handle;
  char pipePath[32];
  int fd;
  int bytes;
  gpioReport_t r[BUF_SIZE];
  uint16_t lastSeqno = 0xffff;
  int entries;
  int i;

  gpioCfgClock(1, 1, 1);

  if ((version = gpioInitialise()) < 0) {
    printf("gpioInitialise error\n");
    return -1;
  }

  printf("version: %d\n", version);

  if (gpioSetTimerFunc(0, 2000, timerFunc) < 0) {
    printf("gpioSetTimerFunc error\n");
  }

  if ((handle = gpioNotifyOpen()) < 0) {
    printf("gpioNotifyOpen error\n");
    return -1;
  }

  if (gpioNotifyBegin(handle, (1 << PULSE_GPIO)) < 0) {
    printf("gpioNotifyBegin error\n");
    return -1;
  }

  sprintf(pipePath, "/dev/pigpio%d", handle);

  if ((fd = open(pipePath, O_RDONLY)) < 0) {
    printf("open error\n");
    return -1;
  }

  for (;;) {
    bytes = read(fd, r, 12 * BUF_SIZE);

    if (bytes <= 0) {
      printf("read error\n");
      return -1;
    }

    entries = bytes / 12;

    if (entries * 12 != bytes) {
      printf("Oops partial entries are not handled");
      return -1;
    }

    for (i = 0; i != entries; ++i) {
      ++notificationCount;

      if (((uint16_t) (lastSeqno + 1)) != r[i].seqno) {
        printf("  sequence error - lastSeqno: %d, seqno: %d\n", lastSeqno, r[i].seqno);
        printf("    %d\n", notificationCount);
      }

      lastSeqno = r[i].seqno;
    }
  }

  gpioTerminate();

  return 0;
}

Here is an example of typical console output on the Pi. As can be seen, some state changes are not detected. In this particular test run sometimes 4 and sometimes 2 state changes were not detected for batches of 100000 state changes.

root@raspberrypi:/home/pi/pigpioc# ./pulsein 
version: 47
100000
100000
199996
199996
199996
299994
299994
299994
399990
399990
499986
499986
499986
599982
599982
599982
699978
699978
799974
799974
799974
899970

Note that it's not essential to generate batches of 50000 pulses to see the issue. It can also be seen with less pulses, but it can take longer to reproduce the issue.

The question is, is this to be expected or is there a problem that needs to be fixed?

Q: SPI communication with BMP183

If you have a moment I would appreciate it very much if you could take a look at what I'm trying to do and explain to me why it is not working. 😃

I have connected a BMP183 to my Pi.
I've connected the instrument as follows:

BMP pin : RPi pin
========:===============
VIN     : 17  (3v3)
3vo     : N/C
GND     : 25  (GND)
SCLK    : 23  (GPIO11)
SDO     : 21  (GPIO09; MISO)
SDI     : 19  (GPIO10; MOSI)
CS      : 24  (GPIO08; CE0)

I've forked the BMP183 python class from PrezmoF and modified it for my implementation. The measure.py program works:

$ sudo python measure.py
[... calibration data in output removed...]
('Temperature: ', 22.899999999999999, 'deg C')
('Pressure: ', 1012.85, ' hPa')

I'm trying to achieve the same effect, but without sudo using the pigpio library in Python.
I've created a small test program: test.py
Sending 0xAA to the instrument should yield a 16-bit word containing the decimal value 8600.
However, running this program returns 1 byte with the value 0.

I've also tried pi.spi_write followed by reading 3 bytes using pi.spi_read. The result is the same. Only 0-values are returned.

Any suggestions are very welcome

Interrupt - Edge Falling - Problem

We are using the PIGPIO python library on a raspberry pi 2 using python 2.7.

Our project has a Raspberry Pi hooked into another PCB that has a micro controller and gpio expander (SX1506). Both the micro controller and SX1506 send interrupts to the raspberry pi via the Pis GPIO (BCM 12 and 26 ). The interrupt is to be sensed by the Pi on a falling edge ( 1->0 ).

We found that if those pins are high (1) when the Pi is turned on, PIGPIO will not create an interrupt the first time the pin goes from 1 -> 0. Once the pin on the GPIO has transitioned from 0 back to 1, PIGPIO will create an interrupt the next time the pin goes from 1 -> 0.

In the code the GPIO pins are set as an Input, and to start a subroutine procedure when the pin senses a falling edged.

Is there some intialization of the GPIO I am missing?

Measure PWM timing

Hi,

I read over the docs two times now and couldn't figure out how to measure the timing of an incoming pulse. In the arduino world, there is a function called pulseIn() for that purpose. Do you provide a similar functionality, which I missed somehow?

Thanks

High CPU utilisation on idle

I notice that, while doing nothing (no I/O events) and no client connected, pigpiod daemon jumps from time to time up to 15% CPU on Raspberry PI 2, and very often stays between 5.7% - 7.6%.

The usage seems too high, do you know how can be reduced?

Thanks,
Dan

PIGPIO under Arch

When you install pigpio under archlinux on raspi, the shared libraries won't be found.

I managed to use it by moving libpigpio.so libpigpiod_if.so and libpigpiod_if2.so from /usr/local/lib to /usr/lib

bad ISR initialisation

The goal of the program below is the following:

  • detect interrupts on GPIO 4 for one seconds with isr1
  • disable interrupts on GPIO 4 for one second
  • detect interrupts on GPIO 4 for one seconds with isr2

However, gpioSetISRFunc(GPIO, EITHER_EDGE, 0, NULL), which I think should disable interrupts is returning -123 which means bad ISR initialisation.

The output of the program is:

version: 38
isr1 - gpio: 4, level: 2
isr1 - gpio: 4, level: 2
isr1 - gpio: 4, level: 2
isr1 - gpio: 4, level: 2
rc: -123

Am I doing something incorrectly?

Additional info:

pi@raspberrypi ~/dev/pigpioc $ cat /etc/debian_version
7.8
pi@raspberrypi ~/dev/pigpioc $ uname -a
Linux raspberrypi 3.18.11-v7+ #781 SMP PREEMPT Tue Apr 21 18:07:59 BST 2015 armv7l GNU/Linux
pi@raspberrypi ~/dev/pigpioc $ 
#include <unistd.h>
#include <stdio.h>
#include <pigpio.h>

#define GPIO 4

void isr1(int gpio, int level, uint32_t tick) {
  printf("isr1 - gpio: %d, level: %d\n", gpio, level);
}

void isr2(int gpio, int level, uint32_t tick) {
  printf("isr2\n");
}

int main(int argc, char *argv[]) {
  int version;
  int rc;

  if ((version = gpioInitialise()) < 0) {
    return -1;
  }

  printf("version: %d\n", version);

  if (gpioSetISRFunc(GPIO, EITHER_EDGE, 200, isr1) != 0) {
    return -1;
  }

  sleep(1);

  if ((rc = gpioSetISRFunc(GPIO, EITHER_EDGE, 0, NULL)) != 0) {
    printf("rc: %d\n", rc); // program prints -123 here which means
    return -1;              // bad ISR initialisation 
  }

  sleep(1);

  if (gpioSetISRFunc(GPIO, EITHER_EDGE, 200, isr2) != 0) {
    return -1;
  }

  sleep(1);

  gpioTerminate();
}

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.