Expected } at end of input error

A common problem, and one that can cause a new programmer to pull their hair out.

However, it's a problem that always has a simple solution, and with the right tricks it's also easy to find where the problem lies.

Let's take the following little code snippet, which throws up this exact error:

byte i = 0;

void doSomething() {
  digitalWrite(3, LOW);
}

void doSomethingElse() {
  digitalWrite(13, HIGH);
}

void setup() {
  // put your setup code here, to run once:
  pinMode(13, OUTPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  if (i == 1) {
    doSomething();
  i++;
}

At first glance that all looks perfectly good. But you compile, and you get:

/home/matt/Arduino/ErrorTest/ErrorTest.ino: In function 'void loop()':
ErrorTest:21: error: expected '}' at end of input
 }
 ^
exit status 1
expected '}' at end of input

Line 21, of course, is the last line of the file. And the error is pretty explicit - it expects a } at the end of the file. However, there is plainly one there already. So what is it on about?

Simply put, there aren't enough } to balance out the number of { in the file. For every { there must be a } to go with it. On this little file it's easy to just go through and count them all. Add one for a { and subtract one for a }. If the answer is not 0 then there's something wrong. But it can take careful looking to see where the missing one should be, and even I have spent hours going cross-eyed trying to find the location in a big project.

There is one little trick, though, that can help you: Auto Format. The Auto Format facility in both the Arduino IDE and UECIDE (and many other IDEs as well) will sort out your indenting for you according to the presence of (amongst other things) { and }.  If the brackets don't match up the formatting would end up wrong.

So let's pass this little program through the auto formatting and see what happens:

byte i = 0;

void doSomething() {
  digitalWrite(3, LOW);
}

void doSomethingElse() {
  digitalWrite(13, HIGH);
}

void setup() {
  // put your setup code here, to run once:
  pinMode(13, OUTPUT);
}

void loop() {
  // put your main code here, to run repeatedly:
  if (i == 1) {
    doSomething();
    i++;
  }

As you can see the loop() function's indenting has changed. And if your eyes are sharp enough you'll already see what was wrong. The "if", which had an opening bracket, didn't have a closing one. The "i++" was supposed to be outside the "if" (as can be seen by the original indenting), but actually it wasn't, and the end of the function was really the end of the "if", leaving the function unfinished.

So fixing it is now really easy. By auto formatting we can see where the imbalance occurs, and fix it:

void loop() {
  // put your main code here, to run repeatedly:
  if (i == 1) {
    doSomething();
  }
  i++;
}

And now it compiles. But of course that little snippet doesn't actually do anything useful...


Arrays? Pointers? What the C?