LJMUAstroecology / flirpy

Python library to interact with FLIR camera cores
Other
193 stars 54 forks source link

PureThermal2 VID/PID mismatch on Mac OS #70

Closed carloscastellanos closed 2 years ago

carloscastellanos commented 2 years ago

Trying to run the simple grab code gives me the following error:

Traceback (most recent call last):
  File "capture_test.py", line 24, in <module>
    image = camera.grab()
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 156, in grab
    self.setup_video(device_id)
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 94, in setup_video
    device_id = self.find_video_device()
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 46, in find_video_device
    if device.contains("VendorID_1E4E") and device.contains("ProductID_0100"):
AttributeError: 'str' object has no attribute 'contains'

Lepton 3.5 PureThermal-2 board Mac OS 10.15.6 Python 3.7.13

jveitchmichaelis commented 2 years ago

Should be fixed (if you re-install from github) https://github.com/LJMUAstroecology/flirpy/commit/b278ad4e0ba91efb621e16bf68f7212b5cc309aa

carloscastellanos commented 2 years ago

Thanks, but now it says the camera is not connected.

Traceback (most recent call last):
  File "capture_test.py", line 24, in <module>
    image = camera.grab()
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 157, in grab
    self.setup_video(device_id)
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 98, in setup_video
    raise ValueError("Lepton not connected.")
ValueError: Lepton not connected.
jveitchmichaelis commented 2 years ago

Can you print the connected device IDs? Either in the code or with lsusb or similar

It'd be good to check if your camera is actually showing up and eg the PID/VID isn't being detected, or if it's something else.

On Wed, 29 Jun 2022 at 11:41, Carlos Castellanos @.***> wrote:

Thanks, but now it says the camera is not connected.

Traceback (most recent call last): File "capture_test.py", line 24, in image = camera.grab() File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 157, in grab self.setup_video(device_id) File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 98, in setup_video raise ValueError("Lepton not connected.") ValueError: Lepton not connected.

— Reply to this email directly, view it on GitHub https://github.com/LJMUAstroecology/flirpy/issues/70#issuecomment-1169764944, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAYDMJ7PNCF6GWBWKES5CDTVRQK5NANCNFSM52D6XTKA . You are receiving this because you modified the open/close state.Message ID: @.***>

carloscastellanos commented 2 years ago

I'm on a Mac so no lsusb so I used system_profiler and it's there:

USB:

    USB 3.1 Bus:

      Host Controller Driver: AppleIntelCNLUSBXHCI
      PCI Device ID: 0xa36d 
      PCI Revision ID: 0x0010 
      PCI Vendor ID: 0x8086 

        USB2.0 HUB:

          Product ID: 0x0101
          Vendor ID: 0x1a40  (TERMINUS TECHNOLOGY INC.)
          Version: 1.00
          Speed: Up to 480 Mb/s
          Location ID: 0x14200000 / 1
          Current Available (mA): 500
          Current Required (mA): 100
          Extra Operating Current (mA): 0

            USB Storage:

              Product ID: 0x0751
              Vendor ID: 0x05e3  (Genesys Logic, Inc.)
              Version: 14.04
              Speed: Up to 480 Mb/s
              Manufacturer: USB Storage
              Location ID: 0x14230000 / 3
              Current Available (mA): 500
              Current Required (mA): 98
              Extra Operating Current (mA): 0

            USB2.0 HUB:

              Product ID: 0x0101
              Vendor ID: 0x1a40  (TERMINUS TECHNOLOGY INC.)
              Version: 1.00
              Speed: Up to 480 Mb/s
              Location ID: 0x14210000 / 2
              Current Available (mA): 500
              Current Required (mA): 100
              Extra Operating Current (mA): 0

                PureThermal (fw:v1.3.0):

                  Product ID: 0x0100
                  Vendor ID: 0x1e4e  (Etron Technology, Inc.)
                  Version: 2.00
                  Serial Number: 00190014-5119-3038-3532-373600000000
                  Speed: Up to 12 Mb/s
                  Manufacturer: GroupGets
                  Location ID: 0x14214000 / 9
                  Current Available (mA): 500
                  Current Required (mA): 100
                  Extra Operating Current (mA): 0

I also ran ioreg and it's there as well:


      | +-o PureThermal (fw:v1.3.0)@14214000  <class AppleUSBDevice, id 0x100001601, registered, matched, active, busy 0 (1 ms), retain 15>
      |     {
      |       "sessionID" = 5918291111404
      |       "idProduct" = 256
      |       "iManufacturer" = 1
      |       "bDeviceClass" = 239
      |       "bMaxPacketSize0" = 64
      |       "bcdDevice" = 512
      |       "iProduct" = 2
      |       "iSerialNumber" = 3
      |       "bNumConfigurations" = 1
      |       "Bus Power Available" = 250
      |       "USB Address" = 9
      |       "Built-In" = No
      |       "locationID" = 337723392
      |       "bDeviceSubClass" = 2
      |       "bcdUSB" = 512
      |       "USB Product Name" = "PureThermal (fw:v1.3.0)"
      |       "PortNum" = 4
      |       "non-removable" = "no"
      |       "kUSBSerialNumberString" = "00190014-5119-3038-3532-373600000000"
      |       "bDeviceProtocol" = 1
      |       "AppleUSBAlternateServiceRegistryID" = 4294972927
      |       "IOCFPlugInTypes" = {"9dc7b780-9ec0-11d4-a54f-000a27052861"="IOUSBHostFamily.kext/Contents/PlugIns/IOUSBLib.bundle"}
      |       "IOPowerManagement" = {"DevicePowerState"=0,"CurrentPowerState"=3,"CapabilityFlags"=65536,"MaxPowerState"=4,"DriverPowerState"=3}
      |       "Device Speed" = 1
      |       "USB Vendor Name" = "GroupGets"
      |       "idVendor" = 7758
      |       "kUSBCurrentConfiguration" = 1
      |       "IOGeneralInterest" = "IOCommand is not serializable"
      |       "kUSBProductString" = "PureThermal (fw:v1.3.0)"
      |       "USB Serial Number" = "00190014-5119-3038-3532-373600000000"
      |       "kUSBVendorString" = "GroupGets"
      |       "IOClassNameOverride" = "IOUSBDevice"
      |     }
      |    
jveitchmichaelis commented 2 years ago

Actually you can run the command the script does (system_profiler SPCameraDataType)

Maybe the device isn’t enumerating as a camera?

(not relevant but there is a version of lsusb in homebrew btw)

carloscastellanos commented 2 years ago

OK I ran system_profiler SPCameraDataType. Seems to enumerate as a camera (and the GroupGets GetThermal app recognizes it just fine)

Camera:

    PureThermal (fw:v1.3.0) #3:

      Model ID: UVC Camera VendorID_7758 ProductID_256
      Unique ID: 0x142140001e4e0100

    FaceTime HD Camera (Built-in):

      Model ID: UVC Camera VendorID_1452 ProductID_34068
      Unique ID: 0x8020000005ac8514
jveitchmichaelis commented 2 years ago

This is a bit odd. The output from system profiler before looks fine (these are the numbers we check for):

Product ID: 0x0100
Vendor ID: 0x1e4e  (Etron Technology, Inc.)

But here you have a different PID/VID:

UVC Camera VendorID_7758 ProductID_256

I guess we ought to check for both, but I'm not sure why it's enumerating as different things. For now, you can go to lepton.py and replace the numbers with those above, but it would be good to figure out why there is a discrepancy here.

jveitchmichaelis commented 2 years ago

You can also use lepton.setup_video(device_id) where device_id is probably 0 or 1. It won't necessarily be robust (sometimes your webcam can switch ID), but if you just want to check your camera, you can set that up manually instead of having flirpy try to find your device automatically.

carloscastellanos commented 2 years ago

Well 7758 is the hex to decimal translation of 0x1e4e. I guess Apple converts it for some reason?

Anyways, I made the changes you suggested but it still didn't work. I get the following errors now:

using camera.setup_video(1):

[ERROR:0] global /private/var/folders/24/8k48jl6d249_n_qfxwsl6xvm0000gn/T/pip-req-build-tetsazc6/opencv/modules/videoio/src/cap.cpp (291) open VIDEOIO(AVFOUNDATION): raised unknown C++ exception!

Traceback (most recent call last):
  File "capture_test.py", line 25, in <module>
    camera.setup_video(1)
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 113, in setup_video
    raise IOError("Failed to open capture device {}".format(device_id))
OSError: Failed to open capture device 1

with only the changes to lepton.py:

Traceback (most recent call last):
  File "capture_test.py", line 26, in <module>
    image = camera.grab()
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 166, in grab
    self.decode_telemetry(image, telemetry_mode)
  File "/Users/ccastellanos/opt/anaconda3/envs/artibmcp-thermal/lib/python3.7/site-packages/flirpy/camera/lepton.py", line 123, in decode_telemetry
    res = struct.unpack("<2cII16x4h6xIh2xh8xhI4xhhhhhh64xI172x", image[-2,:])
struct.error: unpack requires a buffer of 320 bytes

and the builtin-in webcam turns on briefly

jveitchmichaelis commented 2 years ago

Odd well I guess on the macbook I initially used for this it was in hex to begin with. I don't own a PT2 so I can't verify on my newer M1 unfortunately. Easy to fix though, we'll just check for both 🤷‍♂️

If your webcam is blinking then you're probably using the wrong device ID. Did you try 0?

carloscastellanos commented 2 years ago

Yes I tried 0 as well. I'm beginning to think this may be an issue with my Macbook. I'm going to try this on another Mac and see what happens

jveitchmichaelis commented 2 years ago

Can you try with OpenCV directly?

import cv2
devid = 0 # or 1
cap = cv2.VideoCapture(devid)
image = cap.read()
print(image)

Flirpy just creates a VideoCapture object. The GroupGets library (I think?) uses, or at least used to use, a custom UVC driver so they got around limitations with AVFoundation.

carloscastellanos commented 2 years ago

Yes I tried OpenCV as well and that also is not working! I'm getting "an unknown C++ exception".

I've tried installing the groupgets version of libuvc (thinking that might be the issue) but that fails too when I try to run cmake. So not a good for me, lol.

That's actually my original plan. Capture with OpenCV and use flirpy for analysis.

I've also posted on the groupgets googlegroup, so I'm still hopeful I can this working.

carloscastellanos commented 2 years ago

UPDATE: I think I may have figured it out. If run as sudo, this file works: https://github.com/groupgets/purethermal1-uvc-capture/blob/master/python/uvc-radiometry.py

This grabs a stream directly from libuvc. So it seems that at least for now libuvc is the way to go on pure-thermal 2 on MacOS for grabbing a video stream

jveitchmichaelis commented 2 years ago

Yeah it's possible we could bundle libuvc with flirpy and have it load on Mac somehow. I'll see if I can get hold of a PT2 board to test on my laptop, but for now I'd suggest just using the groupgets library.

jveitchmichaelis commented 2 years ago

Closing as this seems to be a somewhat-isolated issue, until we can definitively fix it here there is a solution in the other library.

jveitchmichaelis commented 1 year ago

OK then I suggest printing out each device in the loop to see what's being found (and what the code is testing against)

On Wed, 29 Jun 2022 at 14:25, Carlos Castellanos @.***> wrote:

I'm on a Mac so no lsusb so I used system_profiler and it's there:

USB:

USB 3.1 Bus:

  Host Controller Driver: AppleIntelCNLUSBXHCI
  PCI Device ID: 0xa36d
  PCI Revision ID: 0x0010
  PCI Vendor ID: 0x8086

    USB2.0 HUB:

      Product ID: 0x0101
      Vendor ID: 0x1a40  (TERMINUS TECHNOLOGY INC.)
      Version: 1.00
      Speed: Up to 480 Mb/s
      Location ID: 0x14200000 / 1
      Current Available (mA): 500
      Current Required (mA): 100
      Extra Operating Current (mA): 0

        USB Storage:

          Product ID: 0x0751
          Vendor ID: 0x05e3  (Genesys Logic, Inc.)
          Version: 14.04
          Speed: Up to 480 Mb/s
          Manufacturer: USB Storage
          Location ID: 0x14230000 / 3
          Current Available (mA): 500
          Current Required (mA): 98
          Extra Operating Current (mA): 0

        USB2.0 HUB:

          Product ID: 0x0101
          Vendor ID: 0x1a40  (TERMINUS TECHNOLOGY INC.)
          Version: 1.00
          Speed: Up to 480 Mb/s
          Location ID: 0x14210000 / 2
          Current Available (mA): 500
          Current Required (mA): 100
          Extra Operating Current (mA): 0

            PureThermal (fw:v1.3.0):

              Product ID: 0x0100
              Vendor ID: 0x1e4e  (Etron Technology, Inc.)
              Version: 2.00
              Serial Number: 00190014-5119-3038-3532-373600000000
              Speed: Up to 12 Mb/s
              Manufacturer: GroupGets
              Location ID: 0x14214000 / 9
              Current Available (mA): 500
              Current Required (mA): 100
              Extra Operating Current (mA): 0

I also ran ioreg and it's there as well:

  | +-o PureThermal ***@***.***  <class AppleUSBDevice, id 0x100001601, registered, matched, active, busy 0 (1 ms), retain 15>
  |     {
  |       "sessionID" = 5918291111404
  |       "idProduct" = 256
  |       "iManufacturer" = 1
  |       "bDeviceClass" = 239
  |       "bMaxPacketSize0" = 64
  |       "bcdDevice" = 512
  |       "iProduct" = 2
  |       "iSerialNumber" = 3
  |       "bNumConfigurations" = 1
  |       "Bus Power Available" = 250
  |       "USB Address" = 9
  |       "Built-In" = No
  |       "locationID" = 337723392
  |       "bDeviceSubClass" = 2
  |       "bcdUSB" = 512
  |       "USB Product Name" = "PureThermal (fw:v1.3.0)"
  |       "PortNum" = 4
  |       "non-removable" = "no"
  |       "kUSBSerialNumberString" = "00190014-5119-3038-3532-373600000000"
  |       "bDeviceProtocol" = 1
  |       "AppleUSBAlternateServiceRegistryID" = 4294972927
  |       "IOCFPlugInTypes" = {"9dc7b780-9ec0-11d4-a54f-000a27052861"="IOUSBHostFamily.kext/Contents/PlugIns/IOUSBLib.bundle"}
  |       "IOPowerManagement" = {"DevicePowerState"=0,"CurrentPowerState"=3,"CapabilityFlags"=65536,"MaxPowerState"=4,"DriverPowerState"=3}
  |       "Device Speed" = 1
  |       "USB Vendor Name" = "GroupGets"
  |       "idVendor" = 7758
  |       "kUSBCurrentConfiguration" = 1
  |       "IOGeneralInterest" = "IOCommand is not serializable"
  |       "kUSBProductString" = "PureThermal (fw:v1.3.0)"
  |       "USB Serial Number" = "00190014-5119-3038-3532-373600000000"
  |       "kUSBVendorString" = "GroupGets"
  |       "IOClassNameOverride" = "IOUSBDevice"
  |     }
  |

— Reply to this email directly, view it on GitHub https://github.com/LJMUAstroecology/flirpy/issues/70#issuecomment-1169916977, or unsubscribe https://github.com/notifications/unsubscribe-auth/AAYDMJ34LCDYZZDPFWZRUQDVRQ6D5ANCNFSM52D6XTKA . You are receiving this because you modified the open/close state.Message ID: @.***>