mxgxw / MFRC522-python

A small class to interface with the NFC reader Module MFRC522
GNU Lesser General Public License v3.0
521 stars 419 forks source link

High CPU #17

Open mrStanislav opened 9 years ago

mrStanislav commented 9 years ago

When working with a library MFRC522-python I watched high CPU. About ~ 50%. Please support this issue. Thank you.

msanchezt commented 9 years ago

Same problem here.

brackendawson commented 8 years ago

Not sure if this is in active development, it is more of a demo after all, but my fork is a bit more responsive and a bit less hungry.

mihaj commented 7 years ago

If you use While true loop it consumes a lot of CPU. I have the same problem. How can we use event driven card reads?

brackendawson commented 7 years ago

There is an interrupt line running from the IC. An alternative is to sleep for some pragmatic duration in the loop.

mihaj commented 7 years ago

@brackendawson Is that interrupt Line a IRQ pin? Can you provide more info please. I would appreciate it :).

brackendawson commented 7 years ago

Sorry, I've not looked into what interrupts you can get from it.

LudwigKnuepfer commented 7 years ago

Here is an ugly hack that adds interrupt driven support for waiting for a card detect event.

diff --git a/MFRC522.py b/MFRC522.py
index 6f157c2..735f036 100644
--- a/MFRC522.py
+++ b/MFRC522.py
@@ -4,7 +4,7 @@
 import RPi.GPIO as GPIO
 import spi
 import signal
-import time
+import threading

 class MFRC522:
   NRSTPD = 22
@@ -108,9 +108,12 @@ class MFRC522:
   serNum = []

   def __init__(self, dev='/dev/spidev0.0', spd=1000000):
+    self.irq = threading.Event()
     spi.openSPI(device=dev,speed=spd)
     GPIO.setmode(GPIO.BOARD)
     GPIO.setup(22, GPIO.OUT)
+    GPIO.setup(18, GPIO.IN, pull_up_down=GPIO.PUD_UP)
+    GPIO.add_event_detect(18, GPIO.FALLING, callback=self.input_cb)
     GPIO.output(self.NRSTPD, 1)
     self.MFRC522_Init()

@@ -157,6 +160,8 @@ class MFRC522:
       irqEn = 0x77
       waitIRq = 0x30

     self.Write_MFRC522(self.CommIEnReg, irqEn|0x80)
     self.ClearBitMask(self.CommIrqReg, 0x80)
     self.SetBitMask(self.FIFOLevelReg, 0x80)
@@ -210,6 +215,26 @@ class MFRC522:

     return (status,backData,backLen)

+  def input_cb(self, pin):
+    #print "foobarzoot"
+    self.irq.set()
+    self.Write_MFRC522(self.CommIrqReg, 0x00)
+    self.Write_MFRC522(self.DivIrqReg, 0x00)
+
+  def MFRC522_WaitForCard(self):
+    # enable IRQ on detect
+    self.MFRC522_Init()
+    self.irq.clear()
+    self.Write_MFRC522(self.CommIrqReg, 0x00)
+    self.Write_MFRC522(self.DivIrqReg, 0x00)
+    self.Write_MFRC522(self.CommIEnReg, 0xA0)
+    # wait for it
+    while not self.irq.wait(0.2):
+      self.Write_MFRC522(self.FIFODataReg, self.PICC_REQIDL)
+      self.Write_MFRC522(self.CommandReg, self.PCD_TRANSCEIVE)
+      self.Write_MFRC522(self.BitFramingReg, 0x87)
+    self.irq.clear()
+    self.MFRC522_Init()
diff --git a/Read.py b/Read.py
index 964cd47..6efb202 100755
--- a/Read.py
+++ b/Read.py
@@ -4,6 +4,7 @@
 import RPi.GPIO as GPIO
 import MFRC522
 import signal
+import sys

 continue_reading = True

@@ -13,21 +14,25 @@ def end_read(signal,frame):
   print "Ctrl+C captured, ending read."
   continue_reading = False
   GPIO.cleanup()
+  sys.exit()

-# Hook the SIGINT
-signal.signal(signal.SIGINT, end_read)
+def main():
+  # Hook the SIGINT
+  signal.signal(signal.SIGINT, end_read)

-# Create an object of the class MFRC522
-MIFAREReader = MFRC522.MFRC522()
+  # Create an object of the class MFRC522
+  MIFAREReader = MFRC522.MFRC522()

-# Welcome message
-print "Welcome to the MFRC522 data read example"
-print "Press Ctrl-C to stop."
+  # Welcome message
+  print "Welcome to the MFRC522 data read example"
+  print "Press Ctrl-C to stop."

-# This loop keeps checking for chips. If one is near it will get the UID and authenticate
-while continue_reading:
+  # This loop keeps checking for chips. If one is near it will get the UID and authenticate
+  while continue_reading:
+    # Wait for card
+    MIFAREReader.MFRC522_WaitForCard()

-    # Scan for cards    
+    # Scan card
     (status,TagType) = MIFAREReader.MFRC522_Request(MIFAREReader.PICC_REQIDL)

     # If a card is found
@@ -59,3 +64,5 @@ while continue_reading:
         else:
           print "Authentication error"

+if __name__ == "__main__":
+  main()
i12maroa commented 5 years ago

Hi @LudwigKnuepfer . I have reach this thread because I'm trying to develop a Django login page using a RFID RC522 on a RPi. For read, I'm using the MFRC522.py library. I need to catch an event when a card has been detected to handle the login view and send the RFID ID to the server so I can authenticate users. How can I detect this event?

LudwigKnuepfer commented 5 years ago

go here instead: https://github.com/ondryaso/pi-rc522