Is this function call "delay+(1000)" syntactically correct?
Asked Answered
M

3

5

I am writing a small code to enable a buzzer when a sensor reading is above certain threshold. To enable the buzzer for one second, I gave a delay of 1000ms by calling this function : delay(1000). However, I randomly typed delay+(1000) and it compiles well. Is this function call syntactically correct?

I have tried this code on Arduino IDE. It compiles but the same is not true for avr-gcc or avr-g++ or gcc/g++.

I expect delay+(1000) to not compile as it does not seem to be valid c/c++ syntax.

Update 1:

Compiled and uploaded the following code snippet to Arduino UNO using Arduino IDE :

void setup() 
{
    Serial.begin(9600);
}

void loop()
{
    int x = delay+(1000);
    Serial.println(x);
}

It continuously prints a random number 1132 without any delay. (So, 1132 => Function pointer address + 100 ?)

I also observed that delay+(1000) and delay-(1000) compiles but the same is not true for delay*(1000) and delay/(1000). The compiler gives the following error:

sketch_jun09a:8: error: invalid operands of types 'void(long unsigned int)' and >'int' to binary 'operator*'

     delay*(1000);
               ^

However, this int t = (int)delay*(1000); compiles well.

Update 2:

Based on the answers below, delay<operator>(x) just performs function pointer arithmetic (either using unary or binary operators) and does not execute the function itself.

I have used the following code snippet:

void setup()
{
    Serial.begin(9600);
}
int custom()
{
    Serial.println("hello");
    return 0;
}
void loop()
{
    custom+(1000);
    delay+(1000);
}

It compiles well and outputs nothing.

Update 3:

I changed the Compiler Warnings level to "ALL" under Preferences in Arduino IDE. On compilation of this snippet,

void setup() 
{
    delay+(1000);
}
void loop() {}

Following warnings are obtained :

sketch_jun09a.ino: In function 'void setup()': sketch_jun09a.ino:3:14: warning: pointer to a function used in arithmetic [-Wpointer-arith]

  delay+(1000);
             ^

sketch_jun09a.ino:3:8: warning: statement has no effect [-Wunused-value]

  delay+(1000);
       ^
Mcinerney answered 9/6, 2019 at 3:29 Comment(4)
It looks like it's doing pointer arithmetic by adding 1000 to delay, then discarding the result (unless you assigned it to something). I don't know why it allows this, and I can't imagine how it would be useful.Bezonian
Neither standard C nor standard C++ allow function pointer arithmetic. It seems GCC has an extension for it, however. You should adjust your compilation flags until this becomes a compiler error.Bogbean
@chris: I got you some dictum for the extension.Ministry
@Bogbean I think there is no simple way to adjust compilations flags in the arduino IDE.Tremain
M
9

So there's two things going on here.

delay+(1000)

is syntax for adding 1000 to the function pointer delay. Which of course is completely senseless, but why did it compile at all. Normally you can add integers to pointers, but this would not apply to void * pointers and function pointers. gcc however has an extension that makes adding to void * and void(*)() work by giving the types void and void() size 1. So, adding integers to functions works (uselessly).

It turns out that adding integers to void * pointers is occasionally something you actually want to do and the extension gets rid of a few annoying extra local variables, but function pointers almost never work like that. I guess somebody was building up asm code awhile ago, as it's the only use case I can imagine. Hint: on some architectures, function pointers don't point to function code but to descriptors.

Ministry answered 9/6, 2019 at 3:48 Comment(0)
R
2

I think it adds 1000 to the function pointer, variable, constant or macro expansion of delay but the expression delay+(1000) doesn't do much by itself...

Rozina answered 9/6, 2019 at 3:32 Comment(0)
W
0

Look at Joshua's answer for why. It's a great answer. As for what to do about it, you need to actually call delay.

void setup()
{
    Serial.begin(9600);
}

void loop()
{
    delay(1000);
    Serial.println("Hi there");
}
Wheen answered 11/6, 2019 at 2:4 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.