Skip to content

Generated function prototype injected before declaration of custom parameter type #1269

@allnick

Description

@allnick

The type declared after any function is not visible as the parameter type for any other function below.
Although it is suitable for other purposes.
For example:

struct tword{
  byte low;
  byte high;
};

void none(){}

bool test(tword par){return true;}

void setup() {
  word w;
  tword* var = (tword*)(&w);
}

void loop(){}

It's ok.

void none(){}

struct tword{
  byte low;
  byte high;
};

//bool test(tword par){return true;}

void setup() {
  word w;
  tword* var = (tword*)(&w);
}

void loop(){}

Too it's ok

void none(){}

struct tword{
  byte low;
  byte high;
};

bool test(tword par){return true;}

void setup() {
  word w;
  tword* var = (tword*)(&w);
}

void loop(){}

Compilation fails with the error:

'tword' was not declared in this scope

Additional context

Additional reports

Activity

transferred this issue fromarduino/Arduinoon Apr 18, 2021
per1234

per1234 commented on Apr 18, 2021

@per1234
Contributor

Hi @allnick. Thanks for your report.

During sketch preprocessing, the Arduino build system (which is implemented here in the Arduino CLI code base) automatically generates function prototypes in .ino files for any functions that don't already have a prototype. This turns out to be surprisingly difficult. Although the prototype generation system works fine for most sketches, under certain circumstances, it inserts the prototype at the wrong position in the code. That is the cause of the error you encountered.

You can see how the code looks after preprocessing here:

$ arduino-cli compile --fqbn arduino:avr:uno --preprocess Foo
#include <Arduino.h>
#line 1 "C:\\Foo\\Foo.ino"
#line 1 "C:\\Foo\\Foo.ino"
void none();
#line 8 "C:\\Foo\\Foo.ino"
bool test(tword par);
#line 10 "C:\\Foo\\Foo.ino"
void setup();
#line 15 "C:\\Foo\\Foo.ino"
void loop();
#line 1 "C:\\Foo\\Foo.ino"
void none(){}

struct tword{
  byte low;
  byte high;
};

bool test(tword par){return true;}

void setup() {
  word w;
  tword* var = (tword*)(&w);
}

void loop(){}

Note that the bool test(tword par); prototype was inserted above the declaration of the tword type.

The workaround is to simply manually add your own prototype in the correct location:

void none(){}

struct tword{
  byte low;
  byte high;
};
bool test(tword par); // function prototype
bool test(tword par){return true;}

void setup() {
  word w;
  tword* var = (tword*)(&w);
}

void loop(){}
allnick

allnick commented on Apr 18, 2021

@allnick
Author

Respected per1234. Thanks for your explanation.
But I just moved the type declaration above all the functions.
But your remark, I necessarily take into account.

7 remaining items

Loading
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

conclusion: duplicateHas already been submittedtopic: build-processRelated to the sketch build processtopic: codeRelated to content of the project itselftype: imperfectionPerceived defect in any part of project

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

    Development

    No branches or pull requests

      Participants

      @fstasi@AlbyIanna@per1234@umbynos@rsora

      Issue actions

        Generated function prototype injected before declaration of custom parameter type · Issue #1269 · arduino/arduino-cli