Particle function exposing method in class v1.0.0

Narrowed it down to just the example code producing a hard fault, can anyone else reproduce?

My entire sketch:

// example code
class CoffeeMaker {
  public:
    CoffeeMaker() {
      Particle.function("brew", &CoffeeMaker::brew, this);
    }

    int brew(String command) {
      // do stuff
      return 1;
    }
};

CoffeeMaker myCoffeeMaker;
// nothing else needed in setup() or loop()

void setup() {

}

void loop() {

}

Placing the Particle.function in the setup function works.

class CoffeeMaker {
  public:
    CoffeeMaker() {}
    
    void begin() {
        Particle.function("brew", &CoffeeMaker::brew, this);
    }

    int brew(String command) {
      // do stuff
      Particle.publish("this works");
      return 1;
    }
};

CoffeeMaker myCoffeeMaker;
// nothing else needed in setup() or loop()

void setup() {

    myCoffeeMaker.begin();
    
}

void loop() {

}

or

class CoffeeMaker {
  public:
    CoffeeMaker() {
      Particle.function("brew", &CoffeeMaker::brew, this);
    }

    int brew(String command) {
      // do stuff
      Particle.publish("also works");
      return 1;
    }
};

void setup() {
    
    CoffeeMaker myCoffeeMaker;
    
}

void loop() {

}

The first sketch including method works on a v0.7.0 Photon.

The order of constructors for global objects cannot be guaranteed and the compiler is free to construct them in any order. You cannot depend on the global Particle object being created before your CoffeeMaker object. It worked by random chance in the past.

The right way to handle this is to have a begin method that does your startup work as you show in your second example.

3 Likes

Thanks, makes sense.

The documentation could be explicit but it does already say “nothing else needed in setup() or loop()” implying that it should be in setup. I should buy a lotto ticket, every time before it worked by chance, 1.0.0 discourages that by hard faulting I guess.

1 Like