raspberrypi / linux

Kernel source tree for Raspberry Pi-provided kernel builds. Issues unrelated to the linux kernel should be posted on the community forum at https://forums.raspberrypi.com/
Other
10.95k stars 4.93k forks source link

DHT11.ko (32-bit Bookworm Raspberry Pi OS with a 64-bit kernel) (raspberry pi 4b) #6220

Open Abdulrahman-Yasser opened 2 months ago

Abdulrahman-Yasser commented 2 months ago

Describe the bug

I think DHT11 module doesn't work with my kernel image

Steps to reproduce the behaviour

My aim is to read dht11 from the file system (kernel module) Steps :

  1. Changed my device tree bcm2711-rpi-4-b.dts and added the following lines
    humidity-sensor {
             compatible = "dht11";
             gpios = <&gpio 17 GPIO_ACTIVE_HIGH>;
         }; 
  2. connected my dht data to gpio17 - vcc to rpi.5v - gnd to rpi.gnd
  3. i can find the file in ls -l /sys/bus/iio/devices/iio:device0
  4. output of ls -l /sys/bus/iio/devices/iio:device0 is :
    -rw-r--r-- 1 root root 4096 Jun  7 01:30 in_humidityrelative_input
    -rw-r--r-- 1 root root 4096 Jun  7 01:30 in_temp_input
    -r--r--r-- 1 root root 4096 Jun  7 01:29 name
    lrwxrwxrwx 1 root root    0 Jun  7 01:30 of_node -> ../../../../firmware/devicetree/base/humidity-sensor
    drwxr-xr-x 2 root root    0 Jun  7 01:30 power
    lrwxrwxrwx 1 root root    0 Jun  7 01:30 subsystem -> ../../../../bus/iio
    -rw-r--r-- 1 root root 4096 Jun  7 01:29 uevent
    -r--r--r-- 1 root root 4096 Jun  7 01:30 waiting_for_supplier
  5. I try to read the temperature using the following code :
    sudo cat in_temp_input 

    It shows

    cat: in_temp_input: Input/output error
  6. output of dmesg | tail is
    [   59.967095] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 4
    [   62.719064] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3
    [   64.866734] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3
    [  193.956733] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3
  7. The reading in dmesg is correct. I tried to test it with a lighter and the temperature increased correctly.
  8. I tried to connect dht11 on gpio4 and use a python script to read the data using adafruit-circuitpython-dht and it worked fine (following that article https://pimylifeup.com/raspberry-pi-dht11-sensor/)

Device (s)

Raspberry Pi 4 Mod. B

System

cat /etc/issue :

Raspbian GNU/Linux 12 \n \l

cat /etc/rpi-issue :

Raspberry Pi reference 2024-03-15
Generated using pi-gen, https://github.com/RPi-Distro/pi-gen, 11096428148f0f2be3985ef3126ee71f99c7f1c2, stage5

vcgencmd version :

May 24 2024 15:30:04 
Copyright (c) 2012 Broadcom
version 4942b7633c0ff1af1ee95a51a33b56a9dae47529 (clean) (release) (start)

uname -m :

 aarch64

Logs

[   59.967095] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 4
[   62.719064] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3
[   64.866734] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3
[  193.956733] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3

Additional context

It may be irrelevant. But I am also appended lcd and i2c-gepio-expander to my rpi device tree to work with the modules. Both of them work fine.

fmthola commented 1 month ago

I am having the same issue. After trying to fix the wiring, changing GPIO pins, it still wasn't resolving the issue.

I gave up, and just wrote a python script that would read the dmesg and I would parse it myself.
In your example: [ 193.956733] dht11 humidity-sensor: Don't know how to decode data: 42 0 31 3 42 is the humidity and 31 is the temperature (in C)

The code below only returns the humidity. WIth my sensor, I was getting values that would be 100+ the number. In your example, I would have values that would say 142 instead of just 42. There is logic in this code of if it's greater than 100, it will just ignore and try again.

Program flow:

I know this is a hacky workaround. For my other application, I then simply imported and called this file to get the humidity

import subprocess
import time
import re

def read_humidity():
    try:
        with open('/sys/bus/iio/devices/iio:device0/in_humidityrelative_input', 'r') as file:
            humidity = file.read().strip()
            return humidity
    except Exception as e:
        # Do not print the error
        return None

def get_dmesg_messages():
    try:
        # Capture the output of dmesg
        result = subprocess.run(['dmesg'], stdout=subprocess.PIPE, text=True)
        # Return the output as a list of lines
        return result.stdout.splitlines()
    except Exception as e:
        print(f"Error reading dmesg: {e}")
        return []

def filter_dht11_messages(dmesg_lines):
    dht11_messages = []
    pattern = re.compile(r"dht11.*Don't know how to decode data:")
    for line in dmesg_lines:
        if pattern.search(line):
            dht11_messages.append(line)
    return dht11_messages

def extract_first_number(message):
    match = re.search(r"decode data: (\d+)", message)
    if match:
        return int(match.group(1))
    return None

def main():
    last_dht11_message = None
    last_extracted_number = None

    while True:
        # Read humidity
        humidity = read_humidity()
        if humidity is not None:
            print(f"Humidity: {humidity}%")

        # Wait for 0.1 seconds
        time.sleep(0.1)

        # Get the dmesg messages
        dmesg_lines = get_dmesg_messages()

        # Filter for DHT11-related messages
        dht11_messages = filter_dht11_messages(dmesg_lines)

        # Extract the most recent message if there are any new ones
        if dht11_messages:
            most_recent_message = dht11_messages[-1]
            if most_recent_message != last_dht11_message:
                last_dht11_message = most_recent_message
                extracted_number = extract_first_number(most_recent_message)
                if extracted_number is not None and extracted_number <= 100:
                    last_extracted_number = extracted_number

        # Print the most recent extracted number
        if last_extracted_number is not None:
            print(f"Most recent extracted number: {last_extracted_number}")
        else:
            print("No valid number extracted from DHT11 messages.")

        # Wait before the next iteration
        time.sleep(2)

if __name__ == "__main__":
    main()
ashley-b commented 1 month ago

Am also seeing this error

Software details

Distro: Debain 12.1
kernel version: Linux version 6.6.28-v8+ (dom@buildbot) (aarch64-linux-gnu-gcc (Ubuntu 11.4.0-1ubuntu1~22.04) 11.4.0, GNU ld (GNU Binutils for Ubuntu) 2.38) #1757 SMP PREEMPT Thu Apr 18 11:15:41 BST 2024

lsb_release -a

Distributor ID: Raspbian
Description:    Raspbian GNU/Linux 12 (bookworm)
Release:    12
Codename:   bookworm

Hardware details

Gives this error % 50 of the time otherwise it gives a reasonable value as below

$ cat /sys/bus/iio/devices/iio:device0/in_temp_input
cat: '/sys/bus/iio/devices/iio:device0/in_temp_input': Input/output error

Works some times

$ cat /sys/bus/iio/devices/iio:device0/in_temp_input
31000

dmesg dump

[505002.065451] dht11 dht11@4: Don't know how to decode data: 140 0 15 1
[505012.064921] dht11 dht11@4: Don't know how to decode data: 24 0 30 3
[505012.064929] dht11 dht11@4: Don't know how to decode data: 140 0 15 1
[505022.063812] dht11 dht11@4: Don't know how to decode data: 24 0 30 3
[505022.063821] dht11 dht11@4: Don't know how to decode data: 140 0 15 1
[505032.064904] dht11 dht11@4: Don't know how to decode data: 24 0 30 3
[505032.064914] dht11 dht11@4: Don't know how to decode data: 140 0 15 1
fmthola commented 3 weeks ago

Just an update, I gave the code above that decodes the dmesg, but after a few days that "workaround" wasn't working as dmesg was then reporting it wasn't getting anything at all.

I ordered replacement sensors and when I swapped the existing sensor with a new one, this issue went away and I didn't need my workaround anymore