0
\$\begingroup\$

I have a program on my Arduino Uno that needs to execute quickly, so I'm trying to carry it out by dealing directly with registers. I made a few recent changes to my code, which was originally working fine (unfortunately a change in some of the hardware that's going into this project means I can't revert to the earlier version).

Since the changes, the Uno has developed an issue that I've isolated to one specific problem: I am using an external device to write 0V to the Uno's pin D4 (pinout diagram linked at the bottom of this post), but Serial.print() tells me that pin is getting a 1. I've confirmed the voltage with a multimeter, so either the Arduino is broken or I'm missing something.

const uint8_t pinO = 4; // Register D
void setup() { 
 DDRD &= ~(1<<pinO); // sets pin as input
 PORTD &= ~(1<<pinO); // I wasn't sure I needed this line. Is this what I'm doing wrong?
 Serial.begin(9600);
 }
 void loop() {
 Serial.print((PIND >> daqpinO) && 1);
 }

There's more to the code, but this is everything that should be relevant to the issue. What I see is that writing 3.3V to a different pin on register D seems to be what's causes this pin to start reading high. That shouldn't be happening though, right? All the GPIO pins should be toggled independently?

https://www.google.com/search?q=arduino+uno+pinout&client=firefox-b-1-d&tbm=isch&source=iu&ictx=1&fir=fbbDkYhiQfV2sM%252CFkhuyc9ufXPLnM%252C_&vet=1&usg=AI4_-kR696oFGr1iYjvDWQkqpvcdtaQOGg&sa=X&ved=2ahUKEwi13dL9oNHhAhWtIjQIHftuCXkQ_h0wFnoECAsQBA&biw=1536&bih=750#imgrc=fbbDkYhiQfV2sM:&vet=1

asked Apr 15, 2019 at 4:43
\$\endgroup\$
1
  • \$\begingroup\$ What is it daqpin0? Please put all code. \$\endgroup\$ Commented Apr 15, 2019 at 4:58

3 Answers 3

1
\$\begingroup\$

I think this issue might be with your bit math in the print statement. In the snippet below I've included a typical technique for doing this (see: https://stackoverflow.com/questions/9804866/return-a-specific-bit-as-boolean-from-a-byte-value).

Also, your second line clearing the bit in PORTD after having set it as an input by clearing DDRD will effectively disable the input pull-up resistor on that input. If the source driving your input can drive both high and low (push-pull) that shouldn't be an issue, but if you're just shorting the input to ground (i.e. with a switch or open collector output) you may have undefined behavior (floating input) when the input isn't actively driven. See Arduino's page on port manipulation for more info:

 const uint8_t pinO = 4; // Register D
 
 void setup() { 
 // Clearing DDRD sets the pin to input mode
 DDRD &= ~(1<<pinO);
 // This is the equivalent of digitalWrite and will disable the input pull-up
 PORTD &= ~(1<<pinO);
 
 Serial.begin(9600);
 }
 
 void loop() {
 //Serial.print((PIND >> daqpinO) && 1); <-- This looks like it could be your issue
 //Proposed snippet for checking a bit using a bit-mask
 Serial.print((PIND & (1<<pinO)) != 0);
 }

Edit 1

Added details on why precisely the original version is not working:

Your original statement: (PIND >> daqpinO) && 1 is inadvertently True when pin numbers above 4 are set. This is because && is a LOGICAL AND statement and not a BITWISE AND statement. As an example: let's say that pinO is written LOW and that pin 6 on PORTD is currently written HIGH. The port status would be PIND = 0b01000000. The result of your original statement would be:

 (PIND >> pinO) = 0b00000100
 // Logical AND operation will return True because (PIND >> pinO) is non-zero
 0b00000100 && 1 = True
 // Bitwise AND operation would have returned the intended result 
 // because it would mask out more significant bits
 0b00000100 & 1 = False
answered Apr 15, 2019 at 5:16
\$\endgroup\$
1
\$\begingroup\$

Use single & instead if && to fix it. You need a bitwise AND, not logical AND.

answered Apr 15, 2019 at 5:10
\$\endgroup\$
-1
\$\begingroup\$

Your pin0 is set as an input. You cannot be writing to it. So your statement PORTD &=~(1<

answered Apr 15, 2019 at 4:59
\$\endgroup\$
1
  • 1
    \$\begingroup\$ Writing to PORTD register controls the internal pull-up. So it is normal to write it. In this case it turns the pull-up off. \$\endgroup\$ Commented Apr 15, 2019 at 5:11

Your Answer

Draft saved
Draft discarded

Sign up or log in

Sign up using Google
Sign up using Email and Password

Post as a guest

Required, but never shown

Post as a guest

Required, but never shown

By clicking "Post Your Answer", you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.